package org.jboss.as.test.manualmode.auditlog; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.AUDIT_LOG; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.AUTHENTICATION; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.CORE_SERVICE; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.HANDLER; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.LOCAL; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.MANAGEMENT; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.OUTCOME; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.SECURITY_REALM; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.SUBSYSTEM; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.SUCCESS; import java.io.BufferedReader; import java.io.File; import java.io.IOException; import java.io.StringWriter; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.util.ArrayList; import java.util.List; import java.util.regex.Pattern; import javax.inject.Inject; import javax.management.MBeanServerConnection; import javax.management.ObjectName; import javax.management.remote.JMXConnector; import javax.management.remote.JMXConnectorFactory; import javax.management.remote.JMXServiceURL; import org.jboss.as.controller.PathAddress; import org.jboss.as.controller.PathElement; import org.jboss.as.controller.client.ModelControllerClient; import org.jboss.as.controller.operations.common.Util; import org.jboss.as.domain.management.audit.AuditLogLoggerResourceDefinition; import org.jboss.dmr.ModelNode; import org.junit.After; import org.junit.Assert; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.wildfly.core.testrunner.ServerControl; import org.wildfly.core.testrunner.ServerController; import org.wildfly.core.testrunner.WildflyTestRunner; import org.xnio.IoUtils; /** * @author Ondrej Lukas * * Test that fields of Audit log from JMX have right content */ @RunWith(WildflyTestRunner.class) @ServerControl(manual = true) @Ignore("[WFCORE-1956] Audit logging after migrating to WildFly Elytron.") public class JmxAuditLogFieldsOfLogTestCase { @Inject private ServerController container; private File file; private PathAddress auditLogConfigAddress; private PathAddress mgmtRealmConfigAddress; static JMXConnector connector; static MBeanServerConnection connection; private static final String JMX = "jmx"; private static final String CONFIGURATION = "configuration"; private static final String HANDLER_NAME = "file"; @Test public void testJmxAuditLoggingFields() throws Exception { container.start(); connection = setupAndGetConnection(); if (file.exists()) { file.delete(); } makeOneLog(); Assert.assertTrue(file.exists()); List<ModelNode> logs = readFile(file, 1); ModelNode log = logs.get(0); Assert.assertEquals("jmx", log.get("type").asString()); Assert.assertEquals("true", log.get("r/o").asString()); Assert.assertEquals("false", log.get("booting").asString()); Assert.assertTrue(log.get("version").isDefined()); Assert.assertEquals("IAmAdmin", log.get("user").asString()); Assert.assertFalse(log.get("domainUUID").isDefined()); Assert.assertEquals("JMX", log.get("access").asString()); Assert.assertTrue(log.get("remote-address").isDefined()); Assert.assertEquals("queryMBeans", log.get("method").asString()); List<ModelNode> sig = log.get("sig").asList(); Assert.assertEquals(2, sig.size()); List<ModelNode> params = log.get("params").asList(); Assert.assertEquals(2, params.size()); } private void makeOneLog() throws IOException { ObjectName objectName; try { objectName = ObjectName.getInstance("java.lang:*"); } catch (Exception e) { throw new RuntimeException(e); } connection.queryNames(objectName, null); } @Before public void beforeTest() throws Exception { file = new File(System.getProperty("jboss.home")); file = new File(file, "standalone"); file = new File(file, "data"); file = new File(file, "audit-log.log"); if (file.exists()) { file.delete(); } // Start the server container.start(); final ModelControllerClient client = container.getClient().getControllerClient(); ModelNode op; ModelNode result; mgmtRealmConfigAddress = PathAddress.pathAddress(PathElement.pathElement(CORE_SERVICE, MANAGEMENT), PathElement.pathElement(SECURITY_REALM, "ManagementRealm"), PathElement.pathElement(AUTHENTICATION, LOCAL)); op = Util.getWriteAttributeOperation(mgmtRealmConfigAddress, "default-user", new ModelNode("IAmAdmin")); result = client.execute(op); Assert.assertEquals(result.get("failure-description").asString(), SUCCESS, result.get(OUTCOME).asString()); auditLogConfigAddress = PathAddress.pathAddress(PathElement.pathElement(SUBSYSTEM, JMX), PathElement.pathElement(CONFIGURATION, AUDIT_LOG)); op = Util.createAddOperation(auditLogConfigAddress); result = client.execute(op); Assert.assertEquals(result.get("failure-description").asString(), SUCCESS, result.get(OUTCOME).asString()); op = Util.createAddOperation(PathAddress.pathAddress(auditLogConfigAddress, PathElement.pathElement(HANDLER, HANDLER_NAME))); result = client.execute(op); Assert.assertEquals(result.get("failure-description").asString(), SUCCESS, result.get(OUTCOME).asString()); op = Util.getWriteAttributeOperation(auditLogConfigAddress, AuditLogLoggerResourceDefinition.LOG_READ_ONLY.getName(), new ModelNode(true)); result = client.execute(op); Assert.assertEquals(result.get("failure-description").asString(), SUCCESS, result.get(OUTCOME).asString()); op = Util.getWriteAttributeOperation(auditLogConfigAddress, AuditLogLoggerResourceDefinition.ENABLED.getName(), new ModelNode(true)); result = client.execute(op); Assert.assertEquals(result.get("failure-description").asString(), SUCCESS, result.get(OUTCOME).asString()); container.stop(); } @After public void afterTest() throws Exception { final ModelControllerClient client = container.getClient().getControllerClient(); ModelNode op = Util.getWriteAttributeOperation(mgmtRealmConfigAddress, "default-user", new ModelNode("$local")); client.execute(op); op = Util.getResourceRemoveOperation(PathAddress.pathAddress(auditLogConfigAddress, PathElement.pathElement(HANDLER, HANDLER_NAME))); client.execute(op); op = Util.getResourceRemoveOperation(auditLogConfigAddress); client.execute(op); if (file.exists()) { file.delete(); } IoUtils.safeClose(connector); try { // Stop the container container.stop(); } finally { IoUtils.safeClose(client); } } private MBeanServerConnection setupAndGetConnection() throws Exception { String urlString = System.getProperty("jmx.service.url", "service:jmx:remote+http://" + container.getClient().getMgmtAddress() + ":" + container.getClient().getMgmtPort()); JMXServiceURL serviceURL = new JMXServiceURL(urlString); connector = JMXConnectorFactory.connect(serviceURL, null); return connector.getMBeanServerConnection(); } private final Pattern DATE_STAMP_PATTERN = Pattern.compile("\\d\\d\\d\\d-\\d\\d-\\d\\d \\d\\d:\\d\\d:\\d\\d - \\{"); protected List<ModelNode> readFile(File file, int expectedRecords) throws IOException { List<ModelNode> list = new ArrayList<ModelNode>(); final BufferedReader reader = Files.newBufferedReader(file.toPath(), StandardCharsets.UTF_8); try { StringWriter writer = null; String line = reader.readLine(); while (line != null) { if (DATE_STAMP_PATTERN.matcher(line).matches()) { if (writer != null) { list.add(ModelNode.fromJSONString(writer.getBuffer().toString())); } writer = new StringWriter(); writer.append("{"); } else { writer.append("\n" + line); } line = reader.readLine(); } if (writer != null) { list.add(ModelNode.fromJSONString(writer.getBuffer().toString())); } } finally { IoUtils.safeClose(reader); } Assert.assertEquals(list.toString(), expectedRecords, list.size()); return list; } }