snuk87 / keycloak-kafka Goto Github PK
View Code? Open in Web Editor NEWKeycloak module to produce events to kafka
License: Apache License 2.0
Keycloak module to produce events to kafka
License: Apache License 2.0
Hi!
I would like to be able to use the plugin with the newest version of Keycloak. Do you have plans to update it to work with Keycloak based on Quarkus (17+)?
Hi, I'm running the example with your docker-compose with a little modification.
version: '3'
services:
keycloak:
depends_on:
- "kafka"
image: keycloak-kafka
build:
context: .
ports:
- "8084:8080"
environment:
KEYCLOAK_ADMIN: admin
KEYCLOAK_ADMIN_PASSWORD: admin
KAFKA_TOPIC: keycloak-events
KAFKA_CLIENT_ID: keycloak
KAFKA_BOOTSTRAP_SERVERS: kafka:9094
command: start-dev
zookeeper:
restart: always
image: bitnami/zookeeper:latest
ports:
- "2181:2181"
environment:
- ALLOW_ANONYMOUS_LOGIN=yes
kafka:
depends_on:
- "zookeeper"
image: bitnami/kafka:latest
ports:
- "9092:9092"
- "9094:9094"
environment:
KAFKA_CFG_ADVERTISED_LISTENERS: INSIDE://:9092,OUTSIDE://kafka:9094
KAFKA_CFG_LISTENERS: INSIDE://:9092,OUTSIDE://:9094
KAFKA_CFG_LISTENER_SECURITY_PROTOCOL_MAP: INSIDE:PLAINTEXT,OUTSIDE:PLAINTEXT
KAFKA_CFG_INTER_BROKER_LISTENER_NAME: INSIDE
KAFKA_CFG_ZOOKEEPER_CONNECT: zookeeper:2181
KAFKA_CREATE_TOPICS: "keycloak-events:1:1"
ALLOW_PLAINTEXT_LISTENER: "yes"
volumes:
- /var/run/docker.sock:/var/run/docker.sock
I see that the plugin starts, then I create an event, I can see it in the logs, but no messages are sent to the keycloak-events topic.
Logs:
Updating the configuration and installing your custom providers, if any. Please wait.
2024-03-20 21:02:11,833 WARN [org.keycloak.services] (build-25) KC-SERVICES0047: kafka (com.github.snuk87.keycloak.kafka.KafkaEventListenerProviderFactory) is implementing the internal SPI eventsListener. This SPI is internal and may change without notice
2024-03-20 21:02:13,875 INFO [io.quarkus.deployment.QuarkusAugmentor] (main) Quarkus augmentation completed in 3477ms
2024-03-20 21:02:14,453 INFO [com.github.snuk87.keycloak.kafka.KafkaEventListenerProviderFactory] (main) Init kafka module ...
2024-03-20 21:02:14,489 INFO [org.keycloak.quarkus.runtime.hostname.DefaultHostnameProvider] (main) Hostname settings: Base URL: <unset>, Hostname: <request>, Strict HTTPS: false, Path: <request>, Strict BackChannel: false, Admin URL: <unset>, Admin: <request>, Port: -1, Proxied: false
2024-03-20 21:02:15,024 INFO [org.keycloak.common.crypto.CryptoIntegration] (main) Detected crypto provider: org.keycloak.crypto.def.DefaultCryptoProvider
2024-03-20 21:02:15,603 INFO [org.infinispan.server.core.transport.EPollAvailable] (keycloak-cache-init) ISPN005028: Native Epoll transport not available, using NIO instead: java.lang.UnsatisfiedLinkError: could not load a native library: netty_transport_native_epoll_aarch_64
2024-03-20 21:02:15,612 WARN [org.infinispan.PERSISTENCE] (keycloak-cache-init) ISPN000554: jboss-marshalling is deprecated and planned for removal
2024-03-20 21:02:15,657 WARN [org.infinispan.CONFIG] (keycloak-cache-init) ISPN000569: Unable to persist Infinispan internal caches as no global state enabled
2024-03-20 21:02:15,684 INFO [org.infinispan.CONTAINER] (keycloak-cache-init) ISPN000556: Starting user marshaller 'org.infinispan.jboss.marshalling.core.JBossUserMarshaller'
2024-03-20 21:02:15,830 INFO [org.infinispan.CONTAINER] (keycloak-cache-init) ISPN000128: Infinispan version: Infinispan 'Triskaidekaphobia' 13.0.9.Final
2024-03-20 21:02:16,472 INFO [org.keycloak.quarkus.runtime.storage.legacy.liquibase.QuarkusJpaUpdaterProvider] (main) Initializing database schema. Using changelog META-INF/jpa-changelog-master.xml
2024-03-20 21:02:17,347 INFO [org.keycloak.connections.infinispan.DefaultInfinispanConnectionProviderFactory] (main) Node name: node_363237, Site name: null
2024-03-20 21:02:17,402 INFO [org.keycloak.services] (main) KC-SERVICES0050: Initializing master realm
2024-03-20 21:02:18,191 INFO [io.quarkus] (main) Keycloak 19.0.3 on JVM (powered by Quarkus 2.7.6.Final) started in 4.257s. Listening on: http://0.0.0.0:8080
2024-03-20 21:02:18,191 INFO [io.quarkus] (main) Profile dev activated.
2024-03-20 21:02:18,191 INFO [io.quarkus] (main) Installed features: [agroal, cdi, hibernate-orm, jdbc-h2, jdbc-mariadb, jdbc-mssql, jdbc-mysql, jdbc-oracle, jdbc-postgresql, keycloak, logging-gelf, narayana-jta, reactive-routes, resteasy, resteasy-jackson, smallrye-context-propagation, smallrye-health, smallrye-metrics, vault, vertx]
2024-03-20 21:02:18,391 INFO [org.keycloak.services] (main) KC-SERVICES0009: Added user 'admin' to realm 'master'
2024-03-20 21:02:18,394 WARN [org.keycloak.quarkus.runtime.KeycloakMain] (main) Running the server in development mode. DO NOT use this configuration in production.
2024-03-20 21:02:38,106 INFO [org.apache.kafka.clients.producer.ProducerConfig] (executor-thread-2) ProducerConfig values:
acks = 1
batch.size = 16384
bootstrap.servers = [kafka:9094]
buffer.memory = 33554432
client.dns.lookup = use_all_dns_ips
client.id = keycloak
compression.type = none
connections.max.idle.ms = 540000
delivery.timeout.ms = 120000
enable.idempotence = false
interceptor.classes = []
internal.auto.downgrade.txn.commit = false
key.serializer = class org.apache.kafka.common.serialization.StringSerializer
linger.ms = 0
max.block.ms = 60000
max.in.flight.requests.per.connection = 5
max.request.size = 1048576
metadata.max.age.ms = 300000
metadata.max.idle.ms = 300000
metric.reporters = []
metrics.num.samples = 2
metrics.recording.level = INFO
metrics.sample.window.ms = 30000
partitioner.class = class org.apache.kafka.clients.producer.internals.DefaultPartitioner
receive.buffer.bytes = 32768
reconnect.backoff.max.ms = 1000
reconnect.backoff.ms = 50
request.timeout.ms = 30000
retries = 2147483647
retry.backoff.ms = 100
sasl.client.callback.handler.class = null
sasl.jaas.config = null
sasl.kerberos.kinit.cmd = /usr/bin/kinit
sasl.kerberos.min.time.before.relogin = 60000
sasl.kerberos.service.name = null
sasl.kerberos.ticket.renew.jitter = 0.05
sasl.kerberos.ticket.renew.window.factor = 0.8
sasl.login.callback.handler.class = null
sasl.login.class = null
sasl.login.refresh.buffer.seconds = 300
sasl.login.refresh.min.period.seconds = 60
sasl.login.refresh.window.factor = 0.8
sasl.login.refresh.window.jitter = 0.05
sasl.mechanism = GSSAPI
security.protocol = PLAINTEXT
security.providers = null
send.buffer.bytes = 131072
socket.connection.setup.timeout.max.ms = 30000
socket.connection.setup.timeout.ms = 10000
ssl.cipher.suites = null
ssl.enabled.protocols = [TLSv1.2, TLSv1.3]
ssl.endpoint.identification.algorithm = https
ssl.engine.factory.class = null
ssl.key.password = null
ssl.keymanager.algorithm = SunX509
ssl.keystore.certificate.chain = null
ssl.keystore.key = null
ssl.keystore.location = null
ssl.keystore.password = null
ssl.keystore.type = JKS
ssl.protocol = TLSv1.3
ssl.provider = null
ssl.secure.random.implementation = null
ssl.trustmanager.algorithm = PKIX
ssl.truststore.certificates = null
ssl.truststore.location = null
ssl.truststore.password = null
ssl.truststore.type = JKS
transaction.timeout.ms = 60000
transactional.id = null
value.serializer = class org.apache.kafka.common.serialization.StringSerializer
2024-03-20 21:02:38,164 INFO [org.apache.kafka.common.utils.AppInfoParser] (executor-thread-2) Kafka version: 2.8.0
2024-03-20 21:02:38,164 INFO [org.apache.kafka.common.utils.AppInfoParser] (executor-thread-2) Kafka commitId: ebb1d6e21cc92130
2024-03-20 21:02:38,164 INFO [org.apache.kafka.common.utils.AppInfoParser] (executor-thread-2) Kafka startTimeMs: 1710968558163
2024-03-20 21:02:38,291 INFO [org.apache.kafka.clients.Metadata] (kafka-producer-network-thread | keycloak) [Producer clientId=keycloak] Cluster ID: f3GGvqwZR8SI2MrfknsFig
2024-03-20 21:10:14,344 WARN [org.keycloak.events] (executor-thread-11) type=LOGIN_ERROR, realmId=b2f16f67-0b44-4b8f-a119-2f7dfb4208f1, clientId=null, userId=null, ipAddress=192.168.65.1, error=invalid_request
2024-03-20 21:16:08,038 WARN [org.keycloak.events] (executor-thread-28) type=LOGIN_ERROR, realmId=b2f16f67-0b44-4b8f-a119-2f7dfb4208f1, clientId=security-admin-console, userId=null, ipAddress=192.168.65.1, error=user_not_found, auth_method=openid-connect, auth_type=code, redirect_uri=http://localhost:8084/admin/master/console/#/master/events, code_id=568c7dc2-8801-400b-a44e-addf82e77498, username=sf, authSessionParentId=568c7dc2-8801-400b-a44e-addf82e77498, authSessionTabId=MO_vSyYhWjg
Event:
2024-03-20 21:16:08,038 WARN [org.keycloak.events] (executor-thread-28) type=LOGIN_ERROR, realmId=b2f16f67-0b44-4b8f-a119-2f7dfb4208f1, clientId=security-admin-console, userId=null, ipAddress=192.168.65.1, error=user_not_found, auth_method=openid-connect, auth_type=code, redirect_uri=http://localhost:8084/admin/master/console/#/master/events, code_id=568c7dc2-8801-400b-a44e-addf82e77498, username=sf, authSessionParentId=568c7dc2-8801-400b-a44e-addf82e77498, authSessionTabId=MO_vSyYhWjg
In the keycloak event settings I have selected kafka.
Do you have any ideas? Thanks in advance!
Hello
I'm using Keycloak in Kubernetes, using this Helm chart
I'm using add-kafka-config.cli
(adjustting config file name) - the configs are added.
Also, I've added environment variables to the pod.
When finally I put a jar into deployments
- I receive an error
[org.jboss.msc.service.fail] (MSC service thread 1-2) MSC000001: Failed to start service jboss.deployment.unit."keycloak-kafka-1.1.0-jar-with-dependencies.jar".POST_MODULE: org.jboss.msc.service.StartException in service jboss.deployment.unit."keycloak-kafka-1.1.0-jar-with-dependencies.jar".POST_MODULE: WFLYSRV0153: Failed to process phase POST_MODULE of deployment "keycloak-kafka-1.1.0-jar-with-dependencies.jar"
at [email protected]//org.jboss.as.server.deployment.DeploymentUnitPhaseService.start(DeploymentUnitPhaseService.java:189)
at [email protected]//org.jboss.msc.service.ServiceControllerImpl$StartTask.startService(ServiceControllerImpl.java:1739)
at [email protected]//org.jboss.msc.service.ServiceControllerImpl$StartTask.execute(ServiceControllerImpl.java:1701)
at [email protected]//org.jboss.msc.service.ServiceControllerImpl$ControllerTask.run(ServiceControllerImpl.java:1559)
at [email protected]//org.jboss.threads.ContextClassLoaderSavingRunnable.run(ContextClassLoaderSavingRunnable.java:35)
at [email protected]//org.jboss.threads.EnhancedQueueExecutor.safeRun(EnhancedQueueExecutor.java:1990)
at [email protected]//org.jboss.threads.EnhancedQueueExecutor$ThreadBody.doRunTask(EnhancedQueueExecutor.java:1486)
at [email protected]//org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1363)
at java.base/java.lang.Thread.run(Thread.java:829)
Caused by: java.lang.NullPointerException: topic must not be null.
at deployment.keycloak-kafka-1.1.0-jar-with-dependencies.jar//com.github.snuk87.keycloak.kafka.KafkaEventListenerProviderFactory.init(KafkaEventListenerProviderFactory.java:56)
at [email protected]//org.keycloak.services.DefaultKeycloakSessionFactory.loadFactories(DefaultKeycloakSessionFactory.java:297)
at [email protected]//org.keycloak.services.DefaultKeycloakSessionFactory.deploy(DefaultKeycloakSessionFactory.java:154)
at [email protected]//org.keycloak.provider.ProviderManagerRegistry.deploy(ProviderManagerRegistry.java:42)
at [email protected]//org.keycloak.subsystem.server.extension.KeycloakProviderDeploymentProcessor.deploy(KeycloakProviderDeploymentProcessor.java:58)
at [email protected]//org.jboss.as.server.deployment.DeploymentUnitPhaseService.start(DeploymentUnitPhaseService.java:182)
... 8 more
Basically Scope config
is empty in KafkaEventListenerProviderFactory.init(..)
I've pathced the plugin to read configs parameters directly from environment variables via System.getenv(..)
- and this version works just fine.
Could you please help on the issue ? I can use patched version, but I'd prefer to help debugging and fixing it.
Hello @SnuK87, setting env KAFKA_ENDPOINT_IDENTIFICATION_ALGORITHM= or in keycloak.conf: spi-events-listener-kafka-ssl-endpoint-identification-algorithm= , hasn`t effect, and сertificate continues to be checked.
Can you help with this?
KAFKA_CLIENT_ID=keycloak
KAFKA_ADMIN_TOPIC=raw-keycloak-admin-events
KAFKA_BOOTSTRAP_SERVERS=servers
KAFKA_TOPIC=raw-keycloak-events
KAFKA_SASL_MECHANISM=PLAIN
KAFKA_SECURITY_PROTOCOL=SASL_SSL
KAFKA_SASL_JAAS_CONFIG=org.apache.kafka.common.security.plain.PlainLoginModule required username="username" password="pass";
KAFKA_ENDPOINT_IDENTIFICATION_ALGORITHM=
I can see LOGIN events in the KAFAK topic configured but did not see LOGIN_ERROR event. I have verified that the LOGIN_ERROR is added to KAFKA_EVENTS environment variable.
Hey there, is it possible to run this with auth? I'm trying to make it work with SASL and it always runs into:
javax.security.auth.login.LoginException: unable to find LoginModule class: org.jboss.as.security.remoting.RemotingLoginModule
I assume this has to do with Thread.currentThread().setContextClassLoader(null);
.
But I don't know, how to proceed here. Any Ideas?
Update: asked on https://stackoverflow.com/questions/57574901/kafka-java-client-classloader-doesnt-find-sasl-scram-login-class
Here is the results, when attempting to build using the ./kc.sh build
Tried other images, but it seems thar the curl command is also no longer available after ver19 or higher of keycloak
@SnuK87, congratulations to this project.
During the manual installation it was used standalone.xml
and automatic installation (CLI script) used standalone-ha.xml
. Why ?, What is the correct ?
Hello @SnuK87
we are a bit lost and need your advice.
We are using this extension successfully with older KC versions. Since the migration to KC v19 and after activating
the feature "declarative-user-profiles" and setting User Profile to ON in the Realm, we are getting in our Register Event NULL for both fields.
We are trying to understand why this happens. Can it be that some SPIs and APIs used in the current implementation of the extension are now deprecated or causing this problem?
Many thanks for your help.
BR Mehmet
It's a bit cumbersome to download and copy all the dependencies into the right place.
Better options might be:
deployment
folder of keycloakHello dears. I'm totally new to programming and especially Java. I want to enable SASL authentication without ssl and i made this changes in your KafkaProducerFactory.java:
package com.github.snuk87.keycloak.kafka;
import java.util.Map;
import java.util.Properties;
import org.apache.kafka.clients.producer.KafkaProducer;
import org.apache.kafka.clients.producer.Producer;
import org.apache.kafka.clients.producer.ProducerConfig;
import org.apache.kafka.common.serialization.StringSerializer;
import org.apache.kafka.common.security.scram.ScramLoginModule;
public final class KafkaProducerFactory {
private KafkaProducerFactory() {
}
public static Producer<String, String> createProducer(String clientId, String bootstrapServer,
Map<String, Object> optionalProperties) {
Properties props = new Properties();
props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapServer);
props.put(ProducerConfig.CLIENT_ID_CONFIG, clientId);
props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName());
props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class.getName());
optionalProperties.forEach(props::put);
props.put("security.protocol", "SASL_PLAINTEXT");
props.put("sasl.mechanism", "SCRAM-SHA-512");
props.put("sasl.jaas.config", "org.apache.kafka.common.security.scram.ScramLoginModule required username=\"user\" password=\"pass\";");
// fix Class org.apache.kafka.common.serialization.StringSerializer could not be
// found. see https://stackoverflow.com/a/50981469
Thread.currentThread().setContextClassLoader(null);
return new KafkaProducer<>(props);
}
}
It was built succesfully but when I'm trying to start kafka-spi in keycloak i'm recieving this error:
keycloak_1 | 2023-04-14 14:02:10,403 ERROR [org.keycloak.services.error.KeycloakErrorHandler] (executor-thread-0) Uncaught server error: org.apache.kafka.common.KafkaException: Failed to construct kafka producer
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.<init>(KafkaProducer.java:440)
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.<init>(KafkaProducer.java:291)
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.<init>(KafkaProducer.java:318)
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.<init>(KafkaProducer.java:303)
keycloak_1 | at com.github.snuk87.keycloak.kafka.KafkaProducerFactory.createProducer(KafkaProducerFactory.java:36)
keycloak_1 | at com.github.snuk87.keycloak.kafka.KafkaEventListenerProvider.<init>(KafkaEventListenerProvider.java:53)
keycloak_1 | at com.github.snuk87.keycloak.kafka.KafkaEventListenerProviderFactory.create(KafkaEventListenerProviderFactory.java:29)
keycloak_1 | at com.github.snuk87.keycloak.kafka.KafkaEventListenerProviderFactory.create(KafkaEventListenerProviderFactory.java:12)
keycloak_1 | at org.keycloak.services.DefaultKeycloakSession.getProvider(DefaultKeycloakSession.java:287)
keycloak_1 | at jdk.internal.reflect.GeneratedMethodAccessor20.invoke(Unknown Source)
keycloak_1 | at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
keycloak_1 | at java.base/java.lang.reflect.Method.invoke(Method.java:566)
keycloak_1 | at org.jboss.resteasy.core.ContextParameterInjector$GenericDelegatingProxy.invoke(ContextParameterInjector.java:166)
keycloak_1 | at com.sun.proxy.$Proxy56.getProvider(Unknown Source)
keycloak_1 | at org.keycloak.services.resources.admin.AdminEventBuilder.lambda$addListeners$0(AdminEventBuilder.java:101)
keycloak_1 | at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183)
keycloak_1 | at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:177)
keycloak_1 | at java.base/java.util.Iterator.forEachRemaining(Iterator.java:133)
keycloak_1 | at java.base/java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)
keycloak_1 | at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
keycloak_1 | at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)
keycloak_1 | at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:150)
keycloak_1 | at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:173)
keycloak_1 | at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
keycloak_1 | at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)
keycloak_1 | at org.keycloak.services.resources.admin.AdminEventBuilder.addListeners(AdminEventBuilder.java:100)
keycloak_1 | at org.keycloak.services.resources.admin.AdminEventBuilder.refreshRealmEventsConfig(AdminEventBuilder.java:84)
keycloak_1 | at org.keycloak.services.resources.admin.RealmAdminResource.updateRealmEventsConfig(RealmAdminResource.java:705)
keycloak_1 | at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
keycloak_1 | at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
keycloak_1 | at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
keycloak_1 | at java.base/java.lang.reflect.Method.invoke(Method.java:566)
keycloak_1 | at org.jboss.resteasy.core.MethodInjectorImpl.invoke(MethodInjectorImpl.java:170)
keycloak_1 | at org.jboss.resteasy.core.MethodInjectorImpl.invoke(MethodInjectorImpl.java:130)
keycloak_1 | at org.jboss.resteasy.core.ResourceMethodInvoker.internalInvokeOnTarget(ResourceMethodInvoker.java:660)
keycloak_1 | at org.jboss.resteasy.core.ResourceMethodInvoker.invokeOnTargetAfterFilter(ResourceMethodInvoker.java:524)
keycloak_1 | at org.jboss.resteasy.core.ResourceMethodInvoker.lambda$invokeOnTarget$2(ResourceMethodInvoker.java:474)
keycloak_1 | at org.jboss.resteasy.core.interception.jaxrs.PreMatchContainerRequestContext.filter(PreMatchContainerRequestContext.java:364)
keycloak_1 | at org.jboss.resteasy.core.ResourceMethodInvoker.invokeOnTarget(ResourceMethodInvoker.java:476)
keycloak_1 | at org.jboss.resteasy.core.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:434)
keycloak_1 | at org.jboss.resteasy.core.ResourceLocatorInvoker.invokeOnTargetObject(ResourceLocatorInvoker.java:192)
keycloak_1 | at org.jboss.resteasy.core.ResourceLocatorInvoker.invoke(ResourceLocatorInvoker.java:152)
keycloak_1 | at org.jboss.resteasy.core.ResourceLocatorInvoker.invokeOnTargetObject(ResourceLocatorInvoker.java:183)
keycloak_1 | at org.jboss.resteasy.core.ResourceLocatorInvoker.invoke(ResourceLocatorInvoker.java:141)
keycloak_1 | at org.jboss.resteasy.core.ResourceLocatorInvoker.invoke(ResourceLocatorInvoker.java:32)
keycloak_1 | at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:492)
keycloak_1 | at org.jboss.resteasy.core.SynchronousDispatcher.lambda$invoke$4(SynchronousDispatcher.java:261)
keycloak_1 | at org.jboss.resteasy.core.SynchronousDispatcher.lambda$preprocess$0(SynchronousDispatcher.java:161)
keycloak_1 | at org.jboss.resteasy.core.interception.jaxrs.PreMatchContainerRequestContext.filter(PreMatchContainerRequestContext.java:364)
keycloak_1 | at org.jboss.resteasy.core.SynchronousDispatcher.preprocess(SynchronousDispatcher.java:164)
keycloak_1 | at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:247)
keycloak_1 | at io.quarkus.resteasy.runtime.standalone.RequestDispatcher.service(RequestDispatcher.java:73)
keycloak_1 | at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler.dispatch(VertxRequestHandler.java:151)
keycloak_1 | at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler.handle(VertxRequestHandler.java:82)
keycloak_1 | at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler.handle(VertxRequestHandler.java:42)
keycloak_1 | at io.vertx.ext.web.impl.RouteState.handleContext(RouteState.java:1212)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImplBase.iterateNext(RoutingContextImplBase.java:163)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImpl.next(RoutingContextImpl.java:141)
keycloak_1 | at io.quarkus.vertx.http.runtime.StaticResourcesRecorder$2.handle(StaticResourcesRecorder.java:67)
keycloak_1 | at io.quarkus.vertx.http.runtime.StaticResourcesRecorder$2.handle(StaticResourcesRecorder.java:55)
keycloak_1 | at io.vertx.ext.web.impl.RouteState.handleContext(RouteState.java:1212)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImplBase.iterateNext(RoutingContextImplBase.java:163)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImpl.next(RoutingContextImpl.java:141)
keycloak_1 | at io.quarkus.vertx.http.runtime.VertxHttpRecorder$5.handle(VertxHttpRecorder.java:380)
keycloak_1 | at io.quarkus.vertx.http.runtime.VertxHttpRecorder$5.handle(VertxHttpRecorder.java:358)
keycloak_1 | at io.vertx.ext.web.impl.RouteState.handleContext(RouteState.java:1212)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImplBase.iterateNext(RoutingContextImplBase.java:163)
keycloak_1 | at io.vertx.ext.web.impl.RoutingContextImpl.next(RoutingContextImpl.java:141)
keycloak_1 | at org.keycloak.quarkus.runtime.integration.web.QuarkusRequestFilter.lambda$createBlockingHandler$1(QuarkusRequestFilter.java:90)
keycloak_1 | at io.vertx.core.impl.ContextImpl.lambda$null$0(ContextImpl.java:159)
keycloak_1 | at io.vertx.core.impl.AbstractContext.dispatch(AbstractContext.java:100)
keycloak_1 | at io.vertx.core.impl.ContextImpl.lambda$executeBlocking$1(ContextImpl.java:157)
keycloak_1 | at io.quarkus.vertx.core.runtime.VertxCoreRecorder$13.runWith(VertxCoreRecorder.java:545)
keycloak_1 | at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2449)
keycloak_1 | at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1478)
keycloak_1 | at org.jboss.threads.DelegatingRunnable.run(DelegatingRunnable.java:29)
keycloak_1 | at org.jboss.threads.ThreadLocalResettingRunnable.run(ThreadLocalResettingRunnable.java:29)
keycloak_1 | at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
keycloak_1 | at java.base/java.lang.Thread.run(Thread.java:829)
keycloak_1 | Caused by: org.apache.kafka.common.KafkaException: javax.security.auth.login.LoginException: No LoginModule found for org.apache.kafka.common.security.scram.ScramLoginModule
keycloak_1 | at org.apache.kafka.common.network.SaslChannelBuilder.configure(SaslChannelBuilder.java:184)
keycloak_1 | at org.apache.kafka.common.network.ChannelBuilders.create(ChannelBuilders.java:192)
keycloak_1 | at org.apache.kafka.common.network.ChannelBuilders.clientChannelBuilder(ChannelBuilders.java:81)
keycloak_1 | at org.apache.kafka.clients.ClientUtils.createChannelBuilder(ClientUtils.java:105)
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.newSender(KafkaProducer.java:448)
keycloak_1 | at org.apache.kafka.clients.producer.KafkaProducer.<init>(KafkaProducer.java:429)
keycloak_1 | ... 78 more
keycloak_1 | Caused by: javax.security.auth.login.LoginException: No LoginModule found for org.apache.kafka.common.security.scram.ScramLoginModule
keycloak_1 | at java.base/javax.security.auth.login.LoginContext.invoke(LoginContext.java:731)
keycloak_1 | at java.base/javax.security.auth.login.LoginContext$4.run(LoginContext.java:672)
keycloak_1 | at java.base/javax.security.auth.login.LoginContext$4.run(LoginContext.java:670)
keycloak_1 | at java.base/java.security.AccessController.doPrivileged(Native Method)
keycloak_1 | at java.base/javax.security.auth.login.LoginContext.invokePriv(LoginContext.java:670)
keycloak_1 | at java.base/javax.security.auth.login.LoginContext.login(LoginContext.java:581)
keycloak_1 | at org.apache.kafka.common.security.authenticator.AbstractLogin.login(AbstractLogin.java:60)
keycloak_1 | at org.apache.kafka.common.security.authenticator.LoginManager.<init>(LoginManager.java:62)
keycloak_1 | at org.apache.kafka.common.security.authenticator.LoginManager.acquireLoginManager(LoginManager.java:105)
keycloak_1 | at org.apache.kafka.common.network.SaslChannelBuilder.configure(SaslChannelBuilder.java:170)
keycloak_1 | ... 83 more
Please help me understand what am I doing wrong?
Hello @SnuK87
thanks for your efforts!
We are thinking to use this extension to publish User events e.g. when a user is created.
How will it behave if we scale up the keycloak containers in a cluster and high-availability scenario? As we are serving millions of users, we can not use one single keyloack container.
Is this extension aware of the multiple keycloak instances? To avoid that kafka receives multiple time same event from just another keycloak
If yes, we might use and adjust for usage in
production
Or you think we shall not use in production?
Thanks!
I started getting exceptions when building keycloak 21 with this spi:
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Finished step "io.quarkus.deployment.steps.MainClassBuildStep#build" in 0 ms
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-6) Finished step "io.quarkus.deployment.steps.ReflectionDiagnosticProcessor#writeReflectionData" in 0 ms
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Dependency of "io.quarkus.deployment.pkg.steps.JarResultBuildStep#buildRunnerJar" finished; 1 remaining
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-6) Dependency of "io.quarkus.deployment.pkg.steps.JarResultBuildStep#buildRunnerJar" finished; 0 remaining
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Starting step "io.quarkus.deployment.pkg.steps.JarResultBuildStep#buildRunnerJar"
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Finished step "io.quarkus.deployment.pkg.steps.JarResultBuildStep#buildRunnerJar" in 0 ms
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Dependency of "io.quarkus.deployment.pkg.steps.JarResultBuildStep#jarOutput" finished; 0 remaining
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-1) Dependency of "io.quarkus.deployment.pkg.steps.AppCDSBuildStep#build" finished; 0 remaining
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-6) Starting step "io.quarkus.deployment.pkg.steps.JarResultBuildStep#jarOutput"
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-6) Finished step "io.quarkus.deployment.pkg.steps.JarResultBuildStep#jarOutput" in 0 ms
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-16) Starting step "io.quarkus.deployment.pkg.steps.AppCDSBuildStep#build"
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-6) End step completed; 1 remaining
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-16) Finished step "io.quarkus.deployment.pkg.steps.AppCDSBuildStep#build" in 0 ms
2023-03-01 12:16:31,767 TRACE [io.quarkus.builder] (build-16) End step completed; 0 remaining
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-16) Thread "Thread[build-16,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-30) Thread "Thread[build-30,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-21) Thread "Thread[build-21,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-20) Thread "Thread[build-20,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-15) Thread "Thread[build-15,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-10) Thread "Thread[build-10,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-11) Thread "Thread[build-11,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-6) Thread "Thread[build-6,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-26) Thread "Thread[build-26,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-5) Thread "Thread[build-5,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-12) Thread "Thread[build-12,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-17) Thread "Thread[build-17,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-1) Thread "Thread[build-1,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-9) Thread "Thread[build-9,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-19) Thread "Thread[build-19,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-7) Thread "Thread[build-7,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-24) Thread "Thread[build-24,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-22) Thread "Thread[build-22,5,]" exiting
2023-03-01 12:16:31,767 TRACE [org.jboss.threads] (build-2) Thread "Thread[build-2,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-23) Thread "Thread[build-23,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-3) Thread "Thread[build-3,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-25) Thread "Thread[build-25,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-29) Thread "Thread[build-29,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-4) Thread "Thread[build-4,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-28) Thread "Thread[build-28,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-27) Thread "Thread[build-27,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-18) Thread "Thread[build-18,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-8) Thread "Thread[build-8,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-14) Thread "Thread[build-14,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-13) Thread "Thread[build-13,5,]" exiting
2023-03-01 12:16:31,768 TRACE [org.jboss.threads] (build-31) Thread "Thread[build-31,5,]" exiting
ERROR: Failed to run 'build' command.
Error details:
java.lang.reflect.InvocationTargetException
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at io.quarkus.bootstrap.runner.QuarkusEntryPoint.doReaugment(QuarkusEntryPoint.java:84)
at io.quarkus.bootstrap.runner.QuarkusEntryPoint.doRun(QuarkusEntryPoint.java:48)
at io.quarkus.bootstrap.runner.QuarkusEntryPoint.main(QuarkusEntryPoint.java:32)
at org.keycloak.quarkus.runtime.cli.command.Build.run(Build.java:71)
at picocli.CommandLine.executeUserObject(CommandLine.java:1939)
at picocli.CommandLine.access$1300(CommandLine.java:145)
at picocli.CommandLine$RunLast.executeUserObjectOfLastSubcommandWithSameParent(CommandLine.java:2358)
at picocli.CommandLine$RunLast.handle(CommandLine.java:2352)
at picocli.CommandLine$RunLast.handle(CommandLine.java:2314)
at picocli.CommandLine$AbstractParseResultHandler.execute(CommandLine.java:2179)
at picocli.CommandLine$RunLast.execute(CommandLine.java:2316)
at picocli.CommandLine.execute(CommandLine.java:2078)
at org.keycloak.quarkus.runtime.cli.Picocli.runReAugmentation(Picocli.java:183)
at org.keycloak.quarkus.runtime.cli.Picocli.runReAugmentationIfNeeded(Picocli.java:120)
at org.keycloak.quarkus.runtime.cli.Picocli.parseAndRun(Picocli.java:88)
at org.keycloak.quarkus.runtime.KeycloakMain.main(KeycloakMain.java:88)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at io.quarkus.bootstrap.runner.QuarkusEntryPoint.doRun(QuarkusEntryPoint.java:61)
at io.quarkus.bootstrap.runner.QuarkusEntryPoint.main(QuarkusEntryPoint.java:32)
Caused by: java.lang.RuntimeException: io.quarkus.builder.BuildException: Build failure: Build failed due to errors
[error]: Build step org.keycloak.quarkus.deployment.KeycloakProcessor#setCryptoProvider threw an exception: java.lang.LinkageError: loader constraint violation: loader io.quarkus.bootstrap.classloading.QuarkusClassLoader @14faa38c wants to load class org.keycloak.common.crypto.FipsMode. A different class with the same name was previously loaded by java.net.URLClassLoader @614df0a4. (org.keycloak.common.crypto.FipsMode is in unnamed module of loader java.net.URLClassLoader @614df0a4, parent loader 'app')
at java.base/java.lang.ClassLoader.defineClass1(Native Method)
at java.base/java.lang.ClassLoader.defineClass(ClassLoader.java:1012)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:495)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:455)
at java.base/java.lang.Class.forName0(Native Method)
at java.base/java.lang.Class.forName(Class.java:467)
at io.quarkus.deployment.recording.BytecodeRecorderImpl$$RecordingProxyProxy6.setCryptoProvider(Unknown Source)
at org.keycloak.quarkus.deployment.KeycloakProcessor.setCryptoProvider(KeycloakProcessor.java:636)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at io.quarkus.deployment.ExtensionLoader$3.execute(ExtensionLoader.java:909)
at io.quarkus.builder.BuildContext.run(BuildContext.java:281)
at org.jboss.threads.ContextHandler$1.runWith(ContextHandler.java:18)
at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2449)
at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1478)
at java.base/java.lang.Thread.run(Thread.java:833)
at org.jboss.threads.JBossThread.run(JBossThread.java:501)
at io.quarkus.runner.bootstrap.AugmentActionImpl.runAugment(AugmentActionImpl.java:335)
at io.quarkus.runner.bootstrap.AugmentActionImpl.createProductionApplication(AugmentActionImpl.java:175)
at io.quarkus.deployment.mutability.ReaugmentTask.main(ReaugmentTask.java:69)
... 26 more
Caused by: io.quarkus.builder.BuildException: Build failure: Build failed due to errors
[error]: Build step org.keycloak.quarkus.deployment.KeycloakProcessor#setCryptoProvider threw an exception: java.lang.LinkageError: loader constraint violation: loader io.quarkus.bootstrap.classloading.QuarkusClassLoader @14faa38c wants to load class org.keycloak.common.crypto.FipsMode. A different class with the same name was previously loaded by java.net.URLClassLoader @614df0a4. (org.keycloak.common.crypto.FipsMode is in unnamed module of loader java.net.URLClassLoader @614df0a4, parent loader 'app')
at java.base/java.lang.ClassLoader.defineClass1(Native Method)
at java.base/java.lang.ClassLoader.defineClass(ClassLoader.java:1012)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:495)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:455)
at java.base/java.lang.Class.forName0(Native Method)
at java.base/java.lang.Class.forName(Class.java:467)
at io.quarkus.deployment.recording.BytecodeRecorderImpl$$RecordingProxyProxy6.setCryptoProvider(Unknown Source)
at org.keycloak.quarkus.deployment.KeycloakProcessor.setCryptoProvider(KeycloakProcessor.java:636)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at io.quarkus.deployment.ExtensionLoader$3.execute(ExtensionLoader.java:909)
at io.quarkus.builder.BuildContext.run(BuildContext.java:281)
at org.jboss.threads.ContextHandler$1.runWith(ContextHandler.java:18)
at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2449)
at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1478)
at java.base/java.lang.Thread.run(Thread.java:833)
at org.jboss.threads.JBossThread.run(JBossThread.java:501)
at io.quarkus.builder.Execution.run(Execution.java:123)
at io.quarkus.builder.BuildExecutionBuilder.execute(BuildExecutionBuilder.java:79)
at io.quarkus.deployment.QuarkusAugmentor.run(QuarkusAugmentor.java:160)
at io.quarkus.runner.bootstrap.AugmentActionImpl.runAugment(AugmentActionImpl.java:331)
... 28 more
Caused by: java.lang.LinkageError: loader constraint violation: loader io.quarkus.bootstrap.classloading.QuarkusClassLoader @14faa38c wants to load class org.keycloak.common.crypto.FipsMode. A different class with the same name was previously loaded by java.net.URLClassLoader @614df0a4. (org.keycloak.common.crypto.FipsMode is in unnamed module of loader java.net.URLClassLoader @614df0a4, parent loader 'app')
at java.base/java.lang.ClassLoader.defineClass1(Native Method)
at java.base/java.lang.ClassLoader.defineClass(ClassLoader.java:1012)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:495)
at io.quarkus.bootstrap.classloading.QuarkusClassLoader.loadClass(QuarkusClassLoader.java:455)
at java.base/java.lang.Class.forName0(Native Method)
at java.base/java.lang.Class.forName(Class.java:467)
at io.quarkus.deployment.recording.BytecodeRecorderImpl$$RecordingProxyProxy6.setCryptoProvider(Unknown Source)
at org.keycloak.quarkus.deployment.KeycloakProcessor.setCryptoProvider(KeycloakProcessor.java:636)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at io.quarkus.deployment.ExtensionLoader$3.execute(ExtensionLoader.java:909)
at io.quarkus.builder.BuildContext.run(BuildContext.java:281)
at org.jboss.threads.ContextHandler$1.runWith(ContextHandler.java:18)
at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2449)
at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1478)
at java.base/java.lang.Thread.run(Thread.java:833)
at org.jboss.threads.JBossThread.run(JBossThread.java:501)
The command '/bin/sh -c /opt/keycloak/bin/kc.sh -v build' returned a non-zero code: 1
Cleaning up project directory and file based variables
00:01
ERROR: Job failed: exit code 1
It's hard to establish whether this error is actually caused by a peculiarity of the spi implementation or by some bug in the keycloak itself. The error with fips module is confusing to me - we don't use it and never activated it.
I created an issue in the keycloak repository about this and one of the contributors suggested that the problem is in the spi code itself.
Could you comment on this? If the problem is really with the spi implementation, could you fix it?
P.S.: keycloak/keycloak#16202 is similar to this problem.
Hi @SnuK87,
I'm one of the developers behind Keycloak.
Your project is really interesting and may help many others that also need to optimize how events are processed and stored.
I see a lot of benefits in using a Kafka-based Event Listener Provider, especially when dealing with a huge load of events and how these events are consumed later for audit purposes.
That said, are you interested in adding your project to our site [1]? Is it active and alive?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.