Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add tests for Security Manager #2539

Merged
merged 12 commits into from
Mar 6, 2023
Merged
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
*/
package co.elastic.apm.agent.common.util;

import java.security.AccessControlException;
import java.security.AccessController;
import java.security.PrivilegedAction;

Expand Down Expand Up @@ -54,7 +55,21 @@ public static boolean isDisabled() {
}

private static boolean isDisabledThroughConfiguration() {
return System.getProperty(DISABLED_SYSTEM_PROPERTY) != null || System.getenv(DISABLED_ENV_VARIABLE) != null;
if (System.getSecurityManager() == null) {
return System.getProperty(DISABLED_SYSTEM_PROPERTY) != null || System.getenv(DISABLED_ENV_VARIABLE) != null;
} else {
try {
return AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
@Override
public Boolean run() {
return System.getProperty(DISABLED_SYSTEM_PROPERTY) != null || System.getenv(DISABLED_ENV_VARIABLE) != null;
}
});
} catch (AccessControlException ace) {
// we can't use JVM system properties because security manager prevents it, we'd better be able to log something for the end user
return false;
}
}
}

public static void printStackTrace(Throwable throwable) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,20 @@
*/
package co.elastic.apm.test;

import java.util.Arrays;

public class Main {

public static void main(String[] args) {
System.out.println("Hello World!");

// don't terminate the JVM too fast otherwise the container startup will appear to fail
if (Arrays.asList(args).contains("wait")) {
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
throw new IllegalStateException(e);
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
/*
* Licensed to Elasticsearch B.V. under one or more contributor
* license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright
* ownership. Elasticsearch B.V. licenses this file to you under
* the Apache License, Version 2.0 (the "License"); you may
* not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package co.elastic.apm.test;

import co.elastic.apm.agent.test.AgentFileAccessor;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.io.TempDir;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ValueSource;
import org.testcontainers.containers.GenericContainer;
import org.testcontainers.containers.output.OutputFrame;
import org.testcontainers.containers.wait.strategy.Wait;
import org.testcontainers.containers.wait.strategy.WaitStrategy;

import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardOpenOption;
import java.time.Duration;
import java.util.Arrays;

import static org.assertj.core.api.Assertions.assertThat;

class AgentSetupIT {

@ParameterizedTest
@ValueSource(strings = {"openjdk:8", "openjdk:11", "openjdk:17"})
void testServiceNameAndVersionFromManifest(String image) {
try (GenericContainer<TestAppContainer> app = testAppWithJavaAgent(image)) {

app.waitingFor(Wait.forLogMessage(".* Starting Elastic APM .*", 1))
.start();

assertThat(app.getLogs()).contains(" as My Service Name (My Service Version) on ");
}
}
Comment on lines +44 to +52
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[for reviewer] this was actually tested previously within ServiceTestIT


@Test
void testSecurityManagerWarning() {
String expectedMsg = "Security manager without agent grant-all permission";

try (TestAppContainer app = testAppWithJavaAgent("openjdk:17")) {

app.withSecurityManager()
.waitingFor(Wait.forLogMessage(expectedMsg, 1))
// we expect startup to fail fast as JVM should not even properly start
.withStartupTimeout(Duration.ofSeconds(1));

app.start();

assertThat(app.getLogs(OutputFrame.OutputType.STDERR)).contains(expectedMsg);
}

}

@Test
void testSecurityManagerWithPolicy(@TempDir Path temp) throws IOException {
Path tempPolicy = temp.resolve("security.policy");

// use a 'grant all' policy for now
Files.write(tempPolicy, Arrays.asList(
"grant codeBase \"file:///tmp/elastic-apm-agent.jar\" {",
" permission java.security.AllPermission;",
"};"), StandardOpenOption.CREATE
);

try (TestAppContainer app = testAppWithJavaAgent("openjdk:17")) {
app.withSecurityManager(tempPolicy)
.withStartupTimeout(Duration.ofSeconds(10))
.waitingFor(Wait.forLogMessage(".*Hello World!.*", 1))
.start();
}
}

private TestAppContainer testAppWithJavaAgent(String image) {
return new TestAppContainer(image)
.withAppJar(Path.of("target/main-app-test.jar"))
.withArguments("wait") // make test app wait a bit so we can stop it
.withJavaAgent(AgentFileAccessor.getPathToJavaagent())
// automatically enable remote debug
.withRemoteDebug();
}

}

This file was deleted.