Skip to content

Commit 0efacdb

Browse files
authored
Local ClickHouse cluster configuration (#33)
* Local ClickHouse cluster configuration * Fix `command` and related tests, use more flexible test env, rename configs
1 parent a9c1eca commit 0efacdb

15 files changed

Lines changed: 423 additions & 56 deletions

File tree

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
<?xml version="1.0"?>
2+
<clickhouse>
3+
4+
<http_port>8123</http_port>
5+
<interserver_http_port>9009</interserver_http_port>
6+
<interserver_http_host>clickhouse1</interserver_http_host>
7+
8+
<users_config>users.xml</users_config>
9+
<default_profile>default</default_profile>
10+
<default_database>default</default_database>
11+
12+
<mark_cache_size>5368709120</mark_cache_size>
13+
14+
<path>/var/lib/clickhouse/</path>
15+
<tmp_path>/var/lib/clickhouse/tmp/</tmp_path>
16+
<user_files_path>/var/lib/clickhouse/user_files/</user_files_path>
17+
<access_control_path>/var/lib/clickhouse/access/</access_control_path>
18+
19+
<logger>
20+
<level>debug</level>
21+
<log>/var/log/clickhouse-server/clickhouse-server.log</log>
22+
<errorlog>/var/log/clickhouse-server/clickhouse-server.err.log</errorlog>
23+
<size>1000M</size>
24+
<count>10</count>
25+
<console>1</console>
26+
</logger>
27+
28+
<remote_servers>
29+
<test_cluster>
30+
<shard>
31+
<replica>
32+
<host>clickhouse1</host>
33+
<port>9000</port>
34+
</replica>
35+
<replica>
36+
<host>clickhouse2</host>
37+
<port>9000</port>
38+
</replica>
39+
</shard>
40+
</test_cluster>
41+
</remote_servers>
42+
43+
<keeper_server>
44+
<tcp_port>9181</tcp_port>
45+
<server_id>1</server_id>
46+
<log_storage_path>/var/lib/clickhouse/coordination/log</log_storage_path>
47+
<snapshot_storage_path>/var/lib/clickhouse/coordination/snapshots</snapshot_storage_path>
48+
49+
<coordination_settings>
50+
<operation_timeout_ms>10000</operation_timeout_ms>
51+
<session_timeout_ms>30000</session_timeout_ms>
52+
<raft_logs_level>trace</raft_logs_level>
53+
<rotate_log_storage_interval>10000</rotate_log_storage_interval>
54+
</coordination_settings>
55+
56+
<raft_configuration>
57+
<server>
58+
<id>1</id>
59+
<hostname>clickhouse1</hostname>
60+
<port>9000</port>
61+
</server>
62+
<server>
63+
<id>2</id>
64+
<hostname>clickhouse2</hostname>
65+
<port>9000</port>
66+
</server>
67+
</raft_configuration>
68+
</keeper_server>
69+
70+
<zookeeper>
71+
<node>
72+
<host>clickhouse1</host>
73+
<port>9181</port>
74+
</node>
75+
<node>
76+
<host>clickhouse2</host>
77+
<port>9181</port>
78+
</node>
79+
</zookeeper>
80+
81+
<distributed_ddl>
82+
<path>/clickhouse/test_cluster/task_queue/ddl</path>
83+
</distributed_ddl>
84+
85+
</clickhouse>
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
<clickhouse>
2+
<macros>
3+
<cluster>test_cluster</cluster>
4+
<replica>clickhouse1</replica>
5+
<shard>1</shard>
6+
</macros>
7+
</clickhouse>
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
<?xml version="1.0"?>
2+
<clickhouse>
3+
4+
<http_port>8123</http_port>
5+
<interserver_http_port>9009</interserver_http_port>
6+
<interserver_http_host>clickhouse2</interserver_http_host>
7+
8+
<users_config>users.xml</users_config>
9+
<default_profile>default</default_profile>
10+
<default_database>default</default_database>
11+
12+
<mark_cache_size>5368709120</mark_cache_size>
13+
14+
<path>/var/lib/clickhouse/</path>
15+
<tmp_path>/var/lib/clickhouse/tmp/</tmp_path>
16+
<user_files_path>/var/lib/clickhouse/user_files/</user_files_path>
17+
<access_control_path>/var/lib/clickhouse/access/</access_control_path>
18+
19+
<logger>
20+
<level>debug</level>
21+
<log>/var/log/clickhouse-server/clickhouse-server.log</log>
22+
<errorlog>/var/log/clickhouse-server/clickhouse-server.err.log</errorlog>
23+
<size>1000M</size>
24+
<count>10</count>
25+
<console>1</console>
26+
</logger>
27+
28+
<remote_servers>
29+
<test_cluster>
30+
<shard>
31+
<replica>
32+
<host>clickhouse1</host>
33+
<port>9000</port>
34+
</replica>
35+
<replica>
36+
<host>clickhouse2</host>
37+
<port>9000</port>
38+
</replica>
39+
</shard>
40+
</test_cluster>
41+
</remote_servers>
42+
43+
<keeper_server>
44+
<tcp_port>9181</tcp_port>
45+
<server_id>2</server_id>
46+
<log_storage_path>/var/lib/clickhouse/coordination/log</log_storage_path>
47+
<snapshot_storage_path>/var/lib/clickhouse/coordination/snapshots</snapshot_storage_path>
48+
49+
<coordination_settings>
50+
<operation_timeout_ms>10000</operation_timeout_ms>
51+
<session_timeout_ms>30000</session_timeout_ms>
52+
<raft_logs_level>trace</raft_logs_level>
53+
<rotate_log_storage_interval>10000</rotate_log_storage_interval>
54+
</coordination_settings>
55+
56+
<raft_configuration>
57+
<server>
58+
<id>1</id>
59+
<hostname>clickhouse1</hostname>
60+
<port>9000</port>
61+
</server>
62+
<server>
63+
<id>2</id>
64+
<hostname>clickhouse2</hostname>
65+
<port>9000</port>
66+
</server>
67+
</raft_configuration>
68+
</keeper_server>
69+
70+
<zookeeper>
71+
<node>
72+
<host>clickhouse1</host>
73+
<port>9181</port>
74+
</node>
75+
<node>
76+
<host>clickhouse2</host>
77+
<port>9181</port>
78+
</node>
79+
</zookeeper>
80+
81+
<distributed_ddl>
82+
<path>/clickhouse/test_cluster/task_queue/ddl</path>
83+
</distributed_ddl>
84+
85+
</clickhouse>
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
<clickhouse>
2+
<macros>
3+
<cluster>test_cluster</cluster>
4+
<replica>clickhouse2</replica>
5+
<shard>1</shard>
6+
</macros>
7+
</clickhouse>
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
<?xml version="1.0"?>
2+
<clickhouse>
3+
4+
<profiles>
5+
<default>
6+
<load_balancing>random</load_balancing>
7+
</default>
8+
</profiles>
9+
10+
<users>
11+
<default>
12+
<password></password>
13+
<networks>
14+
<ip>::/0</ip>
15+
</networks>
16+
<profile>default</profile>
17+
<quota>default</quota>
18+
</default>
19+
</users>
20+
21+
<quotas>
22+
<default>
23+
<interval>
24+
<duration>3600</duration>
25+
<queries>0</queries>
26+
<errors>0</errors>
27+
<result_rows>0</result_rows>
28+
<read_rows>0</read_rows>
29+
<execution_time>0</execution_time>
30+
</interval>
31+
</default>
32+
</quotas>
33+
</clickhouse>

.docker/nginx/local.conf

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
upstream clickhouse_cluster {
2+
server clickhouse1:8123;
3+
server clickhouse2:8123;
4+
}
5+
6+
server {
7+
listen 8123;
8+
location / {
9+
proxy_pass http://clickhouse_cluster;
10+
}
11+
}

.github/workflows/run-tests.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,6 @@ jobs:
5252
CLICKHOUSE_CLOUD_HOST: ${{ secrets.CLICKHOUSE_CLOUD_HOST }}
5353
CLICKHOUSE_CLOUD_USERNAME: ${{ secrets.CLICKHOUSE_CLOUD_USERNAME }}
5454
CLICKHOUSE_CLOUD_PASSWORD: ${{ secrets.CLICKHOUSE_CLOUD_PASSWORD }}
55-
CLICKHOUSE_CLOUD_ENABLED: 'true'
55+
CLICKHOUSE_TEST_ENVIRONMENT: 'cloud'
5656
run: |
5757
npm test
Lines changed: 68 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,65 +1,71 @@
11
import { expect } from 'chai';
2-
import { createClient, type ClickHouseClient } from '../../src';
3-
import type { ResponseJSON } from '../../src/clickhouse_types';
2+
import type { ResponseJSON } from '../../src';
3+
import { type ClickHouseClient } from '../../src';
4+
import {
5+
createTestClient,
6+
getClickHouseTestEnvironment,
7+
TestEnv,
8+
} from '../utils/client';
9+
import { guid } from '../utils';
410

511
describe('command', () => {
612
let client: ClickHouseClient;
13+
beforeEach(() => {
14+
client = createTestClient();
15+
});
716
afterEach(async () => {
8-
await client.command({ query: 'DROP TABLE example' });
917
await client.close();
1018
});
1119

1220
it('sends a command to execute', async () => {
13-
client = createClient();
14-
const ddl =
15-
'CREATE TABLE example (id UInt64, name String, sku Array(UInt8), timestamp DateTime) Engine = Memory';
21+
const { ddl, tableName, engine } = getDDL();
1622

17-
await client.command({ query: ddl });
23+
const commandResult = await client.command({
24+
query: ddl,
25+
format: 'TabSeparated',
26+
});
27+
await commandResult.text();
1828

19-
const result = await client.select({
20-
query: `SELECT * from system.tables where name = 'example'`,
29+
const selectResult = await client.select({
30+
query: `SELECT * from system.tables where name = '${tableName}'`,
2131
format: 'JSON',
2232
});
2333

24-
const { data, rows } = await result.json<
34+
const { data, rows } = await selectResult.json<
2535
ResponseJSON<{ name: string; engine: string; create_table_query: string }>
2636
>();
2737

2838
expect(rows).to.equal(1);
2939
const table = data[0];
30-
expect(table.name).equal('example');
31-
expect(table.engine).equal('Memory');
40+
expect(table.name).equal(tableName);
41+
expect(table.engine).equal(engine);
3242
expect(table.create_table_query).to.be.a('string');
3343
});
3444

3545
it('does not swallow ClickHouse error', (done) => {
36-
client = createClient();
37-
38-
const ddl =
39-
'CREATE TABLE example (id UInt64, name String, sku Array(UInt8), timestamp DateTime) Engine = Memory';
40-
46+
const { ddl, tableName } = getDDL();
4147
Promise.resolve()
4248
.then(() => client.command({ query: ddl }))
4349
.then(() => client.command({ query: ddl }))
4450
.catch((e: any) => {
4551
expect(e.code).to.equal('57');
4652
expect(e.type).to.equal('TABLE_ALREADY_EXISTS');
4753
// TODO remove whitespace from end
48-
expect(e.message).equal('Table default.example already exists. ');
54+
expect(e.message).equal(`Table default.${tableName} already exists. `);
4955
done();
5056
});
5157
});
5258

5359
it.skip('can specify a parameterized query', async () => {
54-
client = createClient();
55-
await client.command({
56-
query:
57-
'CREATE TABLE {table_name: String} (id UInt64, name String, sku Array(UInt8), timestamp DateTime) Engine = Memory',
60+
const commandResult = await client.command({
61+
query: '',
5862
query_params: {
5963
table_name: 'example',
6064
},
6165
});
66+
await commandResult.text();
6267

68+
// FIXME: use different DDL based on the TestEnv
6369
const result = await client.select({
6470
query: `SELECT * from system.tables where name = 'example'`,
6571
format: 'JSON',
@@ -74,3 +80,43 @@ describe('command', () => {
7480
expect(table.name).to.equal('example');
7581
});
7682
});
83+
84+
function getDDL(): {
85+
ddl: string;
86+
tableName: string;
87+
engine: string;
88+
} {
89+
const env = getClickHouseTestEnvironment();
90+
const tableName = `command_test_${guid()}`;
91+
switch (env) {
92+
// ENGINE can be omitted in the cloud statements:
93+
// it will use ReplicatedMergeTree and will add ON CLUSTER as well
94+
case TestEnv.Cloud: {
95+
const ddl = `
96+
CREATE TABLE ${tableName}
97+
(id UInt64, name String, sku Array(UInt8), timestamp DateTime)
98+
ORDER BY (id)
99+
`;
100+
return { ddl, tableName, engine: 'ReplicatedMergeTree' };
101+
}
102+
case TestEnv.LocalSingleNode: {
103+
const ddl = `
104+
CREATE TABLE ${tableName}
105+
(id UInt64, name String, sku Array(UInt8), timestamp DateTime)
106+
ENGINE = MergeTree()
107+
ORDER BY (id)
108+
`;
109+
return { ddl, tableName, engine: 'MergeTree' };
110+
}
111+
112+
case TestEnv.LocalCluster: {
113+
const ddl = `
114+
CREATE TABLE ${tableName} ON CLUSTER '{cluster}'
115+
(id UInt64, name String, sku Array(UInt8), timestamp DateTime)
116+
ENGINE ReplicatedMergeTree('/clickhouse/{cluster}/tables/{database}/{table}/{shard}', '{replica}')
117+
ORDER BY (id)
118+
`;
119+
return { ddl, tableName, engine: 'ReplicatedMergeTree' };
120+
}
121+
}
122+
}

0 commit comments

Comments
 (0)