Skip to content

Commit b221f3f

Browse files
matriveddumelendez
andauthored
Add CrateDB module (#6790)
Co-authored-by: Eddú Meléndez <eddu.melendez@gmail.com>
1 parent a692602 commit b221f3f

File tree

18 files changed

+326
-0
lines changed

18 files changed

+326
-0
lines changed

.github/ISSUE_TEMPLATE/bug_report.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ body:
2020
- CockroachDB
2121
- Consul
2222
- Couchbase
23+
- CrateDB
2324
- DB2
2425
- Dynalite
2526
- Elasticsearch

.github/ISSUE_TEMPLATE/enhancement.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ body:
2020
- CockroachDB
2121
- Consul
2222
- Couchbase
23+
- CrateDB
2324
- DB2
2425
- Dynalite
2526
- Elasticsearch

.github/ISSUE_TEMPLATE/feature.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ body:
1818
- Cassandra
1919
- Clickhouse
2020
- CockroachDB
21+
- CrateDB
2122
- Consul
2223
- Couchbase
2324
- DB2

.github/dependabot.yml

+5
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,11 @@ updates:
6262
schedule:
6363
interval: "monthly"
6464
open-pull-requests-limit: 10
65+
- package-ecosystem: "gradle"
66+
directory: "/modules/cratedb"
67+
schedule:
68+
interval: "monthly"
69+
open-pull-requests-limit: 10
6570
- package-ecosystem: "gradle"
6671
directory: "/modules/database-commons"
6772
schedule:

.github/labeler.yml

+2
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919
- modules/consul/**/*
2020
"modules/couchbase":
2121
- modules/couchbase/**/*
22+
"modules/cratedb":
23+
- modules/cratedb/**/*
2224
"modules/db2":
2325
- modules/db2/**/*
2426
"modules/dynalite":

.github/settings.yml

+3
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,9 @@ labels:
124124
- name: modules/couchbase
125125
color: '#006b75'
126126

127+
- name: modules/cratedb
128+
color: '#006b75'
129+
127130
- name: modules/db2
128131
color: '#006b75'
129132

docs/modules/databases/cratedb.md

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
# CrateDB Module
2+
3+
See [Database containers](./index.md) for documentation and usage that is common to all relational database container types.
4+
5+
## Adding this module to your project dependencies
6+
7+
Add the following dependency to your `pom.xml`/`build.gradle` file:
8+
9+
=== "Gradle"
10+
```groovy
11+
testImplementation "org.testcontainers:cratedb:{{latest_version}}"
12+
```
13+
=== "Maven"
14+
```xml
15+
<dependency>
16+
<groupId>org.testcontainers</groupId>
17+
<artifactId>cratedb</artifactId>
18+
<version>{{latest_version}}</version>
19+
<scope>test</scope>
20+
</dependency>
21+
```
22+
23+
!!! hint
24+
Adding this Testcontainers library JAR will not automatically add a database driver JAR to your project. You should ensure that your project also has a suitable database driver as a dependency.
25+

docs/modules/databases/jdbc.md

+4
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,10 @@ Insert `tc:` after `jdbc:` as follows. Note that the hostname, port and database
5151

5252
`jdbc:tc:cockroach:v21.2.3:///databasename`
5353

54+
#### Using CrateDB
55+
56+
`jdbc:tc:cratedb:5.2.3//localhost:5432/crate`
57+
5458
#### Using TiDB
5559

5660
`jdbc:tc:tidb:v6.1.0:///databasename`

mkdocs.yml

+1
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ nav:
5353
- modules/databases/cockroachdb.md
5454
- modules/databases/couchbase.md
5555
- modules/databases/clickhouse.md
56+
- modules/databases/cratedb.md
5657
- modules/databases/db2.md
5758
- modules/databases/dynalite.md
5859
- modules/databases/influxdb.md

modules/cratedb/build.gradle

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
description = "Testcontainers :: JDBC :: CrateDB"
2+
3+
dependencies {
4+
annotationProcessor 'com.google.auto.service:auto-service:1.0.1'
5+
compileOnly 'com.google.auto.service:auto-service:1.0.1'
6+
7+
api project(':jdbc')
8+
9+
testImplementation project(':jdbc-test')
10+
testImplementation 'org.postgresql:postgresql:42.5.4'
11+
12+
compileOnly 'org.jetbrains:annotations:24.0.0'
13+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
package org.testcontainers.cratedb;
2+
3+
import org.jetbrains.annotations.NotNull;
4+
import org.testcontainers.containers.JdbcDatabaseContainer;
5+
import org.testcontainers.containers.wait.strategy.Wait;
6+
import org.testcontainers.utility.DockerImageName;
7+
8+
import java.util.Set;
9+
10+
public class CrateDBContainer extends JdbcDatabaseContainer<CrateDBContainer> {
11+
12+
static final String NAME = "cratedb";
13+
14+
static final String IMAGE = "crate";
15+
16+
static final String DEFAULT_TAG = "5.2.5";
17+
18+
private static final DockerImageName DEFAULT_IMAGE_NAME = DockerImageName.parse("crate");
19+
20+
static final Integer CRATEDB_PG_PORT = 5432;
21+
22+
static final Integer CRATEDB_HTTP_PORT = 4200;
23+
24+
private String databaseName = "crate";
25+
26+
private String username = "crate";
27+
28+
private String password = "crate";
29+
30+
public CrateDBContainer(final String dockerImageName) {
31+
this(DockerImageName.parse(dockerImageName));
32+
}
33+
34+
public CrateDBContainer(final DockerImageName dockerImageName) {
35+
super(dockerImageName);
36+
dockerImageName.assertCompatibleWith(DEFAULT_IMAGE_NAME);
37+
38+
this.waitStrategy = Wait.forHttp("/").forPort(CRATEDB_HTTP_PORT).forStatusCode(200);
39+
40+
addExposedPort(CRATEDB_PG_PORT);
41+
addExposedPort(CRATEDB_HTTP_PORT);
42+
}
43+
44+
/**
45+
* @return the ports on which to check if the container is ready
46+
* @deprecated use {@link #getLivenessCheckPortNumbers()} instead
47+
*/
48+
@NotNull
49+
@Override
50+
@Deprecated
51+
protected Set<Integer> getLivenessCheckPorts() {
52+
return super.getLivenessCheckPorts();
53+
}
54+
55+
@Override
56+
public String getDriverClassName() {
57+
return "org.postgresql.Driver";
58+
}
59+
60+
@Override
61+
public String getJdbcUrl() {
62+
String additionalUrlParams = constructUrlParameters("?", "&");
63+
return (
64+
"jdbc:postgresql://" +
65+
getHost() +
66+
":" +
67+
getMappedPort(CRATEDB_PG_PORT) +
68+
"/" +
69+
databaseName +
70+
additionalUrlParams
71+
);
72+
}
73+
74+
@Override
75+
public String getDatabaseName() {
76+
return databaseName;
77+
}
78+
79+
@Override
80+
public String getUsername() {
81+
return username;
82+
}
83+
84+
@Override
85+
public String getPassword() {
86+
return password;
87+
}
88+
89+
@Override
90+
public String getTestQueryString() {
91+
return "SELECT 1";
92+
}
93+
94+
@Override
95+
public CrateDBContainer withDatabaseName(final String databaseName) {
96+
this.databaseName = databaseName;
97+
return self();
98+
}
99+
100+
@Override
101+
public CrateDBContainer withUsername(final String username) {
102+
this.username = username;
103+
return self();
104+
}
105+
106+
@Override
107+
public CrateDBContainer withPassword(final String password) {
108+
this.password = password;
109+
return self();
110+
}
111+
112+
@Override
113+
protected void waitUntilContainerStarted() {
114+
getWaitStrategy().waitUntilReady(this);
115+
}
116+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
package org.testcontainers.cratedb;
2+
3+
import org.testcontainers.containers.JdbcDatabaseContainer;
4+
import org.testcontainers.containers.JdbcDatabaseContainerProvider;
5+
import org.testcontainers.jdbc.ConnectionUrl;
6+
import org.testcontainers.utility.DockerImageName;
7+
8+
/**
9+
* Factory for CrateDB containers using PostgreSQL JDBC driver.
10+
*/
11+
public class CrateDBContainerProvider extends JdbcDatabaseContainerProvider {
12+
13+
public static final String USER_PARAM = "user";
14+
15+
public static final String PASSWORD_PARAM = "password";
16+
17+
@Override
18+
public boolean supports(String databaseType) {
19+
return databaseType.equals(CrateDBContainer.NAME);
20+
}
21+
22+
@Override
23+
public JdbcDatabaseContainer newInstance() {
24+
return newInstance(CrateDBContainer.DEFAULT_TAG);
25+
}
26+
27+
@Override
28+
public JdbcDatabaseContainer newInstance(String tag) {
29+
return new CrateDBContainer(DockerImageName.parse(CrateDBContainer.IMAGE).withTag(tag));
30+
}
31+
32+
@Override
33+
public JdbcDatabaseContainer newInstance(ConnectionUrl connectionUrl) {
34+
return newInstanceFromConnectionUrl(connectionUrl, USER_PARAM, PASSWORD_PARAM);
35+
}
36+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
org.testcontainers.cratedb.CrateDBContainerProvider
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
package org.testcontainers;
2+
3+
import org.testcontainers.utility.DockerImageName;
4+
5+
public interface CrateDBTestImages {
6+
DockerImageName CRATEDB_TEST_IMAGE = DockerImageName.parse("crate:5.2.5");
7+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
package org.testcontainers.jdbc.cratedb;
2+
3+
import org.junit.runner.RunWith;
4+
import org.junit.runners.Parameterized;
5+
import org.testcontainers.jdbc.AbstractJDBCDriverTest;
6+
7+
import java.util.Arrays;
8+
import java.util.EnumSet;
9+
10+
@RunWith(Parameterized.class)
11+
public class CrateDBJDBCDriverTest extends AbstractJDBCDriverTest {
12+
13+
@Parameterized.Parameters(name = "{index} - {0}")
14+
public static Iterable<Object[]> data() {
15+
return Arrays.asList(
16+
new Object[][] {
17+
{ "jdbc:tc:cratedb:5.2.3://hostname/crate?user=crate&password=somepwd", EnumSet.noneOf(Options.class) },
18+
}
19+
);
20+
}
21+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
package org.testcontainers.junit.cratedb;
2+
3+
import org.junit.Test;
4+
import org.testcontainers.CrateDBTestImages;
5+
import org.testcontainers.cratedb.CrateDBContainer;
6+
import org.testcontainers.db.AbstractContainerDatabaseTest;
7+
8+
import java.sql.ResultSet;
9+
import java.sql.SQLException;
10+
import java.util.logging.Level;
11+
import java.util.logging.LogManager;
12+
13+
import static org.assertj.core.api.Assertions.assertThat;
14+
15+
public class SimpleCrateDBTest extends AbstractContainerDatabaseTest {
16+
static {
17+
// Postgres JDBC driver uses JUL; disable it to avoid annoying, irrelevant, stderr logs during connection testing
18+
LogManager.getLogManager().getLogger("").setLevel(Level.OFF);
19+
}
20+
21+
@Test
22+
public void testSimple() throws SQLException {
23+
try (CrateDBContainer cratedb = new CrateDBContainer(CrateDBTestImages.CRATEDB_TEST_IMAGE)) {
24+
cratedb.start();
25+
26+
ResultSet resultSet = performQuery(cratedb, "SELECT 1");
27+
int resultSetInt = resultSet.getInt(1);
28+
assertThat(resultSetInt).as("A basic SELECT query succeeds").isEqualTo(1);
29+
assertHasCorrectExposedAndLivenessCheckPorts(cratedb);
30+
}
31+
}
32+
33+
@Test
34+
public void testCommandOverride() throws SQLException {
35+
try (
36+
CrateDBContainer cratedb = new CrateDBContainer(CrateDBTestImages.CRATEDB_TEST_IMAGE)
37+
.withCommand("crate -C cluster.name=testcontainers")
38+
) {
39+
cratedb.start();
40+
41+
ResultSet resultSet = performQuery(cratedb, "select name from sys.cluster");
42+
String result = resultSet.getString(1);
43+
assertThat(result).as("cluster name should be overriden").isEqualTo("testcontainers");
44+
}
45+
}
46+
47+
@Test
48+
public void testExplicitInitScript() throws SQLException {
49+
try (
50+
CrateDBContainer cratedb = new CrateDBContainer(CrateDBTestImages.CRATEDB_TEST_IMAGE)
51+
.withInitScript("somepath/init_cratedb.sql")
52+
) {
53+
cratedb.start();
54+
55+
ResultSet resultSet = performQuery(cratedb, "SELECT foo FROM bar");
56+
57+
String firstColumnValue = resultSet.getString(1);
58+
assertThat(firstColumnValue).as("Value from init script should equal real value").isEqualTo("hello world");
59+
}
60+
}
61+
62+
private void assertHasCorrectExposedAndLivenessCheckPorts(CrateDBContainer cratedb) {
63+
assertThat(cratedb.getExposedPorts()).containsExactly(5432, 4200);
64+
assertThat(cratedb.getLivenessCheckPortNumbers())
65+
.containsExactlyInAnyOrder(cratedb.getMappedPort(5432), cratedb.getMappedPort(4200));
66+
}
67+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<configuration>
2+
3+
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
4+
<!-- encoders are assigned the type
5+
ch.qos.logback.classic.encoder.PatternLayoutEncoder by default -->
6+
<encoder>
7+
<pattern>%d{HH:mm:ss.SSS} %-5level %logger - %msg%n</pattern>
8+
</encoder>
9+
</appender>
10+
11+
<root level="INFO">
12+
<appender-ref ref="STDOUT"/>
13+
</root>
14+
15+
<logger name="org.testcontainers" level="INFO"/>
16+
</configuration>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
CREATE TABLE bar (
2+
foo STRING
3+
);
4+
5+
INSERT INTO bar (foo) VALUES ('hello world');
6+
REFRESH TABLE bar;

0 commit comments

Comments
 (0)