I am trying to write a test case for testing read/write access to a Google Cloud Bucket using Spring Boot (v2.7.5). For this I tried to use the 'Testcontainer' framework in combination with a fake Google Cloud Storage container (fake-gcs-server).
The problem is that the app does not start with this configuration. The error message is "The Application Default Credentials are not available."
I have set the '.setCredentials(NoCredentials.getInstance())' but that does not help.
@SpringBootTest
@TestInstance(TestInstance.Lifecycle.PER_CLASS) // Share data between the test methods
@TestMethodOrder(MethodOrderer.OrderAnnotation.class) // Enable ordering of test methods
@Testcontainers
class GPSStorageTest {
private static final String BUCKET_NAME = "BUCKET_TEST";
private static final Integer INTERNAL_PORT = 8888;
protected static Storage storage = null;
// Set the GenericContainer to 'static' and the GenericContainer will be shared between test methods
@Container
private static final GenericContainer<?>gcsFakeContainer =
new GenericContainer<>(DockerImageName.parse("fsouza/fake-gcs-server:latest"))
.withCommand("-port",INTERNAL_PORT.toString(), "-scheme", "http")
.withExposedPorts(8888)
.waitingFor(Wait.forHttp("/").forStatusCode(404))
.withReuse(true);
@BeforeAll
public static void setup() {
int mappedPort = gcsFakeContainer.getMappedPort(INTERNAL_PORT);
StorageOptions storageOps = StorageOptions.newBuilder()
.setCredentials(NoCredentials.getInstance())
.setHost("http://" + gcsFakeContainer.getHost() + ":" + mappedPort)
.setProjectId("TEST_LOCAL")
.build();
storage = storageOps.getService();
}
@Test
@Order(1)
public void testCreateBucket() {
createBucket();
Assertions.assertTrue(checkBucketExists());
}
@Test
@Order(2)
public void testIfFileWritten() {
String filename = "test.txt";
Bucket bucket = storage.get(BUCKET_NAME);
bucket.create(filename, "Hello, World!".getBytes(UTF_8));
Assertions.assertTrue(fileExits(filename));
}
private boolean fileExits(String filename) {
return storage.get(BUCKET_NAME,filename) != null;
}
private void createBucket() {
try {
storage.create(BucketInfo.of(BUCKET_NAME));
} catch (Exception ex) {
System.err.println("Error creating bucket");
ex.printStackTrace();
}
}
private boolean checkBucketExists() {
return storage.get(BUCKET_NAME, Storage.BucketGetOption.fields()) != null;
}
}
Does anyone have any ideas on how I can get it to work?
Update I put the previous class in a small demo project to demonstrate the problem: https://github.com/benocms/de.test.testcontainers
I fixed the problem.
This configuration disables the automatic Spring Boot configuration of the cloud.gcp.storage API.
application.properties:
spring.cloud.gcp.storage.enabled=false
Update
This configuration is also possible in the test class itself:
@DynamicPropertySource
static void gcsFakeProperties(DynamicPropertyRegistry registry) {
registry.add("spring.cloud.gcp.storage.enabled",()-> false);
}
Note: The @DynamicPropertySource annotation is only available since Spring Boot >= 2.2.6.