package org.gcube.keycloak.event; import java.net.InetAddress; import java.net.UnknownHostException; import java.time.Instant; import java.time.OffsetDateTime; import java.time.ZoneOffset; import java.util.Map; import org.gcube.event.publisher.Event; import org.json.simple.JSONObject; import org.json.simple.parser.JSONParser; import org.json.simple.parser.ParseException; import org.keycloak.events.admin.AdminEvent; public class KeycloakEvent extends Event { private static final long serialVersionUID = 4072256389444123291L; public static final String TYPE = "keycloak"; // Common fields public static final String REALM = "realm"; // Admin event fields public static final String OPERATION = "operation"; public static final String REPRESENTATION = "representation"; public static final String RESOURCE = "resource"; public static final String RESOURCE_TYPE = "resource-type"; // Event fields public static final String CLIENT = "client"; public static final String ERROR = "error"; public static final String SESSION = "session"; public static final String REMOTE_ADDRESS = "remote-address"; public static final String USER = "user"; public static final String EVENT_NAME_PREFIX = "keycloak_"; public static final String ADMIN_NAME = "admin"; public static String HOST_NAME; static { try { HOST_NAME = InetAddress.getLocalHost().getCanonicalHostName(); } catch (UnknownHostException e) { // Almost impossible e.printStackTrace(); } } private KeycloakEvent(String name, String realm, long time) { this(name, realm, time, null); } private KeycloakEvent(String name, String realm, long time, Map data) { super(EVENT_NAME_PREFIX + name, TYPE, HOST_NAME, data); // Overriding the timestamp setting it equal to the event time setTimestamp(convertEventDate(time)); setRealm(realm); } public static KeycloakEvent newKeycloakAdminEvent(AdminEvent adminEvent, boolean includeRepresentation) { KeycloakEvent keycloakEvent = new KeycloakEvent(ADMIN_NAME, adminEvent.getRealmId(), adminEvent.getTime()); keycloakEvent.setOperation(adminEvent.getOperationType().name()); if (includeRepresentation) { keycloakEvent.setRepresentation(adminEvent.getRepresentation()); } keycloakEvent.setResource(adminEvent.getResourcePath()); keycloakEvent.setResourceType(adminEvent.getResourceTypeAsString()); return keycloakEvent; } public static KeycloakEvent newKeycloakEvent(org.keycloak.events.Event event) { KeycloakEvent keycloakEvent = new KeycloakEvent(event.getType().name().toLowerCase(), event.getRealmId(), event.getTime(), event.getDetails()); keycloakEvent.setError(event.getError()); keycloakEvent.setClient(event.getClientId()); keycloakEvent.setRemoteAddress(event.getIpAddress()); keycloakEvent.setSession(event.getSessionId()); keycloakEvent.setUser(event.getUserId()); // Adding event specific details in opaque mode event.getDetails().forEach((key, value) -> keycloakEvent.set(key, value)); return keycloakEvent; } private static OffsetDateTime convertEventDate(long millis) { OrchestratorEventPublisherProvider.logger.debugf("Creating offset date time from millis %d -> %t", millis, millis); return Instant.ofEpochMilli(millis).atZone(ZoneOffset.systemDefault()).toOffsetDateTime(); } public void setRealm(String realm) { set(REALM, realm); } public String getRealm() { return (String) get(REALM); } @SuppressWarnings("unchecked") public void setRepresentation(String representation) { try { put(REPRESENTATION, new JSONParser().parse(representation)); } catch (ParseException e) { e.printStackTrace(); set(REPRESENTATION, representation); } } public String getRepresentation() { return ((JSONObject) get(REPRESENTATION)).toString(); } public void setResource(String resource) { set(RESOURCE, resource); } public String getResource() { return (String) get(RESOURCE); } public void setResourceType(String resourceType) { set(RESOURCE_TYPE, resourceType); } public String getResourceType() { return (String) get(RESOURCE_TYPE); } public void setClient(String client) { set(CLIENT, client); } public String getClient() { return (String) get(CLIENT); } public void setError(String error) { set(ERROR, error); } public String getError() { return (String) get(ERROR); } public void setOperation(String operation) { set(OPERATION, operation); } public String getOperation() { return (String) get(OPERATION); } public void setRemoteAddress(String remoteAddress) { set(REMOTE_ADDRESS, remoteAddress); } public String getRemoteAddress() { return (String) get(REMOTE_ADDRESS); } public void setSession(String session) { set(SESSION, session); } public String getSession() { return (String) get(SESSION); } public void setUser(String user) { set(USER, user); } public String getUser() { return (String) get(USER); } }