Skip to content

Commit 7a4a3d4

Browse files
p3rf Teamcopybara-github
authored andcommitted
Onboard KVrocks Memtier benchmark.
PiperOrigin-RevId: 815736286
1 parent 56c211c commit 7a4a3d4

File tree

8 files changed

+911
-13
lines changed

8 files changed

+911
-13
lines changed

CHANGES.next.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,7 @@
257257
- Add support for the `--addons` flag in GKE Standard.
258258
- Add support for RHEL and Rocky Linux 10.
259259
- Add support for Debian 13.
260+
- Add KVRocks memtier benchmark with LSSD support.
260261

261262
### Enhancements:
262263

perfkitbenchmarker/configs/default_benchmark_config.yaml

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -567,3 +567,21 @@ diskspd_max_throughput_write_only:
567567
flags:
568568
<<: *diskspd_write_only_flags
569569
<<: *diskspd_max_throughput_flags
570+
571+
kvrocks_memtier:
572+
name: kvrocks_memtier
573+
flags:
574+
fio_fill_block_size: 64k
575+
data_disk_type: local
576+
num_striped_disks: 8
577+
memtier_protocol: 'redis'
578+
memtier_cluster_mode: True
579+
memtier_clients: 1
580+
memtier_threads: 4
581+
memtier_pipeline: 1
582+
memtier_data_size: 400
583+
memtier_key_maximum: 18000000
584+
memtier_key_prefix: 'key'
585+
memtier_run_duration: 40
586+
memtier_random_data: True
587+
memtier_command: 'hmset __key__ field1 __data__ field2 __data__ field3 __data__ field4 __data__ field5 __data__ field6 __data__ field7 __data__ field8 __data__ field9 __data__ field10 __data__ field11 __data__ field12 __data__ field13 __data__ field14 __data__ field15 __data__ field16 __data__ field17 __data__ field18 __data__ field19 __data__'
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
daemonize yes
2+
timeout 0
3+
slowlog-max-len 128
4+
cluster-enabled yes
5+
rocksdb.max_write_buffer_number 16
6+
rocksdb.write_buffer_size 64
7+
rocksdb.max_background_jobs 4
8+
rocksdb.max_bytes_for_level_base 2147483647
9+
rocksdb.compression no
10+
workers 16
11+
max-replication-mb 500
12+
migrate-batch-rate-limit-mb 64
13+
cluster-enabled yes
14+
persist-cluster-nodes-enabled yes
15+
bind 0.0.0.0
16+
maxclients 60000
17+
rocksdb.block_size 4096
18+
migrate-speed 0
19+
migrate-pipeline-size 64
20+
migrate-batch-size-kb 64
21+
tcp-backlog 4096
22+
log-level warning
23+
slowlog-log-slower-than 20000
24+
rocksdb.level0_file_num_compaction_trigger 8
25+
# rocksdb.min_write_buffer_number_to_merge 4
26+
# rocksdb.max_sub_compactions 1
27+
rocksdb.compaction_readahead_size 1048576 #128k, max_sector_kb
28+
rocksdb.level0_slowdown_writes_trigger 30
29+
rocksdb.level0_stop_writes_trigger 60
30+
rocksdb.level0_file_num_compaction_trigger 8
31+
rocksdb.stats_dump_period_sec 60
32+
rocksdb.stats_dump_period_sec 60
33+
rocksdb.enable_pipelined_write yes
34+
# rocksdb.use_direct_reads no
35+
migrate-type raw-key-value
36+
rocksdb.wal_ttl_seconds 3600
37+
rocksdb.wal_size_limit_mb 32768
38+
requirepass {{password}}
39+
masterauth {{password}}
40+
max-db-size 256
41+
rocksdb.block_cache_size 16000
42+
log-retention-days 7
43+
44+
45+
port {{port}}
46+
dir /data/kv-{{instance_num}}
47+
log-dir /data/kv-{{instance_num}}/log
48+
backup-dir /data/kv-{{instance_num}}/backup
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
# prometheus.yml
2+
global:
3+
scrape_interval: 5s
4+
query_log_file: /prometheus/query.log
5+
scrape_configs:
6+
- job_name: 'kvrocks_exporter_targets'
7+
static_configs:
8+
- targets:
9+
{% for kvrocks_instance in kvrocks_instances %}
10+
- kvrocks://{{kvrocks_instance.ip_address}}:{{kvrocks_instance.port}}
11+
{% endfor %}
12+
metrics_path: /scrape
13+
relabel_configs:
14+
- source_labels: [__address__]
15+
target_label: __param_target
16+
- source_labels: [__param_target]
17+
target_label: instance
18+
- target_label: __address__
19+
replacement: {{kvrocks_exporter.ip_address}}:9180
20+
- job_name: 'kvrocks_exporter'
21+
static_configs:
22+
- targets:
23+
- {{kvrocks_exporter.ip_address}}:9180
Lines changed: 199 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,199 @@
1+
# Copyright 2025 PerfKitBenchmarker Authors. All rights reserved.
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
"""Run memtier_benchmark against a KVrocks cluster."""
16+
17+
import logging
18+
from typing import Any, Dict, List
19+
20+
from absl import flags
21+
from perfkitbenchmarker import background_tasks
22+
from perfkitbenchmarker import benchmark_spec
23+
from perfkitbenchmarker import configs
24+
from perfkitbenchmarker import errors
25+
from perfkitbenchmarker import sample
26+
from perfkitbenchmarker.linux_packages import kvrocks_server
27+
from perfkitbenchmarker.linux_packages import memtier
28+
from perfkitbenchmarker.linux_packages import prometheus
29+
30+
FLAGS = flags.FLAGS
31+
32+
BENCHMARK_NAME = 'kvrocks_memtier'
33+
BENCHMARK_CONFIG = """
34+
kvrocks_memtier:
35+
description: >
36+
Run memtier_benchmark against KVrocks.
37+
vm_groups:
38+
servers:
39+
vm_spec:
40+
GCP:
41+
machine_type: c3-standard-44-lssd
42+
vm_count: 3
43+
os_type: rocky-9
44+
disk_spec:
45+
GCP:
46+
disk_type: local
47+
num_striped_disks: 8
48+
mount_point: /scratch
49+
AWS:
50+
disk_type: local
51+
num_striped_disks: 8
52+
mount_point: /scratch
53+
Azure:
54+
disk_type: local
55+
num_striped_disks: 8
56+
mount_point: /scratch
57+
clients:
58+
vm_spec:
59+
GCP:
60+
machine_type: n2-standard-64
61+
vm_count: 1
62+
os_type: rocky-9
63+
disk_spec:
64+
GCP:
65+
disk_type: local
66+
num_striped_disks: 8
67+
mount_point: /scratch
68+
AWS:
69+
disk_type: local
70+
num_striped_disks: 8
71+
mount_point: /scratch
72+
Azure:
73+
disk_type: local
74+
num_striped_disks: 8
75+
mount_point: /scratch
76+
"""
77+
78+
79+
_BenchmarkSpec = benchmark_spec.BenchmarkSpec
80+
81+
82+
def GetConfig(user_config: Dict[str, Any]) -> Dict[str, Any]:
83+
"""Load and return benchmark config spec."""
84+
return configs.LoadConfig(BENCHMARK_CONFIG, user_config, BENCHMARK_NAME)
85+
86+
87+
def CheckPrerequisites(_):
88+
"""Verifies that benchmark setup is correct."""
89+
pass
90+
91+
92+
def Prepare(bm_spec: _BenchmarkSpec) -> None:
93+
"""Install and set up KVrocks and client tools."""
94+
server_vms = bm_spec.vm_groups['servers']
95+
client_vms = bm_spec.vm_groups['clients']
96+
vms = server_vms + client_vms
97+
98+
background_tasks.RunThreaded(lambda vm: vm.Install('kvrocks_server'), vms)
99+
background_tasks.RunThreaded(lambda vm: vm.Install('memtier'), client_vms)
100+
101+
def _InstallAndStartPrometheus(vm):
102+
vm.Install('prometheus')
103+
prometheus.ConfigureAndStart(vm, server_vms)
104+
105+
background_tasks.RunThreaded(_InstallAndStartPrometheus, client_vms)
106+
107+
# Skipping preconditioning for now.
108+
# TODO(user): Add preconditioning.
109+
kvrocks_server.StartCluster(server_vms)
110+
111+
def _StartExporter(vm):
112+
kvrocks_server.StartExporter(vm)
113+
114+
# The prometheus server on the client is configured to scrape exporters
115+
# from the server VMs.
116+
background_tasks.RunThreaded(_StartExporter, server_vms)
117+
118+
prometheus.WaitUntilHealthy(client_vms[0])
119+
120+
# Check cluster status
121+
master_vm = server_vms[0]
122+
123+
try:
124+
cluster_info, _ = kvrocks_server.RunRedisCommand(
125+
master_vm, '-c cluster info'
126+
)
127+
logging.info('KVrocks cluster info: %s', cluster_info)
128+
cluster_nodes, _ = kvrocks_server.RunRedisCommand(
129+
master_vm, '-c cluster nodes'
130+
)
131+
logging.info('KVrocks cluster nodes: %s', cluster_nodes)
132+
except errors.VirtualMachine.RemoteCommandError as e:
133+
logging.warning('KVrocks cluster not ready or redis commands failed: %s', e)
134+
135+
136+
def Run(bm_spec: _BenchmarkSpec) -> List[sample.Sample]:
137+
"""Run the memtier benchmark and collect results."""
138+
client_vms = bm_spec.vm_groups['clients']
139+
server_vms = bm_spec.vm_groups['servers']
140+
master_vm = server_vms[0]
141+
ip = master_vm.internal_ip
142+
ports = list(kvrocks_server.INSTANCE_TO_PORT_MAP.values())
143+
144+
logging.info('Starting memtier runs...')
145+
try:
146+
results = memtier.RunOverAllThreadsPipelinesAndClients(
147+
client_vms, ip, [ports[0]], kvrocks_server.GetPassword()
148+
)
149+
except errors.VirtualMachine.RemoteCommandError as e:
150+
logging.exception('Memtier run failed: %s', e)
151+
results = []
152+
logging.info('Memtier runs finished. Results: %s', results)
153+
154+
metadata = kvrocks_server.GetMetadata()
155+
for res in results:
156+
res.metadata.update(metadata)
157+
158+
# Query prometheus stats from the first client
159+
client_vm = client_vms[0]
160+
161+
slowlog_total = prometheus.RunQuery(client_vm, 'sum(kvrocks_slowlog_total)')
162+
commands_total = prometheus.RunQuery(
163+
client_vm, 'sum(kvrocks_commands_total{cmd="hmset"})'
164+
)
165+
slowlog_ratio = prometheus.RunQuery(
166+
client_vm,
167+
'sum(kvrocks_slowlog_total) / sum(kvrocks_commands_total{cmd="hmset"})',
168+
)
169+
170+
logging.info('Slowlog total: %s', slowlog_total)
171+
logging.info('Commands total: %s', commands_total)
172+
logging.info('Slowlog ratio: %s', slowlog_ratio)
173+
174+
if slowlog_total is not None:
175+
results.append(
176+
sample.Sample('KVRocks Slowlog Total', slowlog_total, 'count', metadata)
177+
)
178+
179+
if commands_total is not None:
180+
results.append(
181+
sample.Sample(
182+
'KVRocks Commands Total HMSET',
183+
commands_total,
184+
'count',
185+
metadata,
186+
)
187+
)
188+
189+
if slowlog_ratio is not None:
190+
results.append(
191+
sample.Sample('KVRocks Slowlog Ratio', slowlog_ratio, 'ratio', metadata)
192+
)
193+
194+
return results
195+
196+
197+
def Cleanup(bm_spec: _BenchmarkSpec) -> None:
198+
"""Cleanup resources."""
199+
del bm_spec

0 commit comments

Comments
 (0)