نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

این حتی یک شوخی نیست، به نظر می رسد که این تصویر خاص به درستی ماهیت این پایگاه های داده را منعکس می کند، و در پایان مشخص خواهد شد که چرا:

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

بر اساس رتبه بندی موتورهای DB، دو پایگاه داده ستونی NoSQL محبوب ترین، Cassandra (از این پس CS) و HBase (HB) هستند.

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

به خواست سرنوشت، تیم مدیریت بارگیری داده ما در Sberbank قبلاً انجام شده است مدتها پیش و از نزدیک با HB کار می کند. در این مدت به خوبی نقاط قوت و ضعف آن را مطالعه کردیم و طرز پخت آن را یاد گرفتیم. با این حال، وجود یک جایگزین به شکل CS همیشه ما را مجبور می کرد کمی خود را با شک و تردید عذاب دهیم: آیا انتخاب درستی انجام دادیم؟ علاوه بر این، نتایج مقایسه ها، انجام شده توسط DataStax، آنها گفتند که CS به راحتی HB را با تقریباً یک امتیاز خرد کننده شکست می دهد. از طرف دیگر، DataStax یک طرف علاقه مند است و شما نباید حرف آنها را قبول کنید. ما همچنین از اطلاعات نسبتاً کمی در مورد شرایط آزمایش گیج شده بودیم، بنابراین تصمیم گرفتیم خودمان بدانیم که پادشاه BigData NoSql کیست و نتایج به دست آمده بسیار جالب بود.

با این حال، قبل از حرکت به سمت نتایج آزمایش‌های انجام‌شده، لازم است جنبه‌های مهم پیکربندی محیط شرح داده شود. واقعیت این است که CS را می توان در حالتی استفاده کرد که اجازه از دست دادن داده ها را می دهد. آن ها این زمانی است که فقط یک سرور (گره) مسئول داده های یک کلید خاص است و اگر به دلایلی از کار بیفتد، ارزش این کلید از بین می رود. برای بسیاری از وظایف این امر حیاتی نیست، اما برای بخش بانکی این یک استثنا است تا یک قاعده. در مورد ما، داشتن چندین نسخه از داده ها برای ذخیره سازی قابل اعتماد مهم است.

بنابراین، تنها حالت عملیاتی CS در حالت تکرار سه گانه در نظر گرفته شد، یعنی. ایجاد فضای پرونده با پارامترهای زیر انجام شد:

CREATE KEYSPACE ks WITH REPLICATION = {'class' : 'NetworkTopologyStrategy', 'datacenter1' : 3};

در مرحله بعد، دو راه برای اطمینان از سطح مورد نیاز از سازگاری وجود دارد. قانون کلی:
NW + NR > RF

این بدان معناست که تعداد تأییدات از گره ها هنگام نوشتن (NW) به اضافه تعداد تأییدات از گره ها هنگام خواندن (NR) باید بیشتر از ضریب تکرار باشد. در مورد ما، RF = 3، به این معنی که گزینه های زیر مناسب هستند:
2 + 2 > 3
3 + 1 > 3

از آنجایی که اساساً برای ما مهم است که داده ها را تا حد امکان قابل اعتماد ذخیره کنیم، طرح 3+1 انتخاب شد. علاوه بر این، HB بر اساس یک اصل مشابه کار می کند، یعنی. چنین مقایسه ای منصفانه تر خواهد بود.

لازم به ذکر است که DataStax در مطالعه خود برعکس عمل کرد، آنها RF = 1 را برای هر دو CS و HB تنظیم کردند (برای دومی با تغییر تنظیمات HDFS). این یک جنبه واقعاً مهم است زیرا تأثیر آن بر عملکرد CS در این مورد بسیار زیاد است. به عنوان مثال، تصویر زیر افزایش زمان مورد نیاز برای بارگذاری داده ها در CS را نشان می دهد:

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

در اینجا موارد زیر را مشاهده می کنیم: هر چه رشته های رقیب بیشتر داده ها را بنویسند، زمان بیشتری طول می کشد. این طبیعی است، اما مهم است که کاهش عملکرد برای RF=3 به طور قابل توجهی بالاتر باشد. به عبارت دیگر، اگر 4 رشته را در 5 جدول بنویسیم (در مجموع 20)، آنگاه RF=3 حدود 2 برابر می‌بازد (150 ثانیه برای RF=3 در مقابل 75 برای RF=1). اما اگر با بارگذاری داده ها در 8 جدول با 5 رشته (در مجموع 40 رشته) بار را افزایش دهیم، آنگاه از دست دادن RF=3 در حال حاضر 2,7 برابر است (375 ثانیه در مقابل 138).

شاید تا حدودی این راز تست بار موفقیت آمیز انجام شده توسط DataStax برای CS باشد، زیرا برای HB در غرفه ما تغییر ضریب تکرار از 2 به 3 هیچ تاثیری نداشت. آن ها دیسک ها گلوگاه HB برای پیکربندی ما نیستند. با این حال، بسیاری از دام های دیگر در اینجا وجود دارد، زیرا باید توجه داشت که نسخه HB ما کمی وصله و بهینه سازی شده بود، محیط ها کاملاً متفاوت هستند و غیره. همچنین شایان ذکر است که شاید من نمی دانم چگونه CS را به درستی آماده کنم و راه های موثرتری برای کار با آن وجود دارد و امیدوارم در نظرات متوجه شویم. اما اول از همه.

تمام تست‌ها بر روی یک خوشه سخت‌افزاری متشکل از 4 سرور، هر کدام با پیکربندی زیر انجام شد:

CPU: Xeon E5-2680 v4 @ 2.40GHz 64 Thread.
دیسک ها: 12 قطعه SATA HDD
نسخه جاوا: 1.8.0_111

نسخه CS: 3.11.5

پارامترهای cassandra.ymlnum_tokens: 256
hinted_handoff_enabled: درست است
hinted_handoff_throttle_in_kb: 1024
max_hints_delivery_threads: 2
hints_directory: /data10/cassandra/hints
hints_flush_period_in_ms: 10000
max_hints_file_size_in_mb: 128
batchlog_replay_throttle_in_kb: 1024
authenticator: AllowAllAuthenticator
autorizer: AllowAllAuthorizer
role_manager: CassandraRoleManager
roles_validity_in_ms: 2000
permissions_validity_in_ms: 2000
credentials_validity_in_ms: 2000
پارتیشن: org.apache.cassandra.dht.Murmur3Partitioner
data_file_directories:
- /data1/cassandra/data # هر فهرست dataN یک دیسک جداگانه است
- /data2/cassandra/data
- /data3/cassandra/data
- /data4/cassandra/data
- /data5/cassandra/data
- /data6/cassandra/data
- /data7/cassandra/data
- /data8/cassandra/data
commitlog_directory: /data9/cassandra/commitlog
cdc_enabled: نادرست
disk_failure_policy: توقف
commit_failure_policy: توقف کنید
ready_statements_cache_size_mb:
thrift_prepared_statements_cache_size_mb:
key_cache_size_in_mb:
key_cache_save_period: 14400
row_cache_size_in_mb: 0
row_cache_save_period: 0
counter_cache_size_in_mb:
counter_cache_save_period: 7200
saved_caches_directory: /data10/cassandra/saved_caches
commitlog_sync: دوره ای
commitlog_sync_period_in_ms: 10000
commitlog_segment_size_in_mb: 32
seed_provider:
- class_name: org.apache.cassandra.locator.SimpleSeedProvider
پارامتر:
- دانه: "*،*"
همزمان با خواندن: 256 # سعی شد 64 - تفاوتی مشاهده نشد
همزمان_نوشته: 256 # امتحان شده 64 - تفاوتی مشاهده نشد
concurrent_counter_writes: 256 # سعی کردم 64 - تفاوتی مشاهده نشد
concurrent_materialized_view_writes: 32
memtable_heap_space_in_mb: 2048 # 16 گیگابایت امتحان شد - کندتر بود
memtable_allocation_type: heap_buffers
index_summary_capacity_in_mb:
index_summary_resize_interval_in_minutes: 60
trickle_fsync: نادرست
trickle_fsync_interval_in_kb: 10240
Storage_port: 7000
ssl_storage_port: 7001
listen_address: *
آدرس_پخش: *
listen_on_broadcast_address: درست است
internode_authenticator: org.apache.cassandra.auth.AllowAllInternodeAuthenticator
start_native_transport: درست است
Native_transport_port: 9042
start_rpc: درست است
rpc_address: *
rpc_port: 9160
rpc_keepalive: درست است
rpc_server_type: همگام سازی
thrift_framed_transport_size_in_mb: 15
incremental_backups: false
snapshot_before_compaction: false
auto_snapshot: درست است
column_index_size_in_kb: 64
column_index_cache_size_in_kb: 2
متراکم کننده های همزمان: 4
compaction_throughput_mb_per_sec: 1600
sstable_preemptive_open_interval_in_mb: 50
read_request_timeout_in_ms: 100000
range_request_timeout_in_ms: 200000
write_request_timeout_in_ms: 40000
counter_write_request_timeout_in_ms: 100000
cas_contention_timeout_in_ms: 20000
truncate_request_timeout_in_ms: 60000
request_timeout_in_ms: 200000
slow_query_log_timeout_in_ms: 500
cross_node_timeout: نادرست
endpoint_snitch: GossipingPropertyFileSnitch
dynamic_snitch_update_interval_in_ms: 100
dynamic_snitch_reset_interval_in_ms: 600000
dynamic_snitch_badness_threshold: 0.1
request_scheduler: org.apache.cassandra.scheduler.NoScheduler
server_encryption_options:
internode_encryption: هیچ
client_encryption_options:
فعال: نادرست
internode_compression: dc
inter_dc_tcp_nodelay: نادرست
tracetype_query_ttl: 86400
tracetype_repair_ttl: 604800
enable_user_defined_functions: نادرست
enable_scripted_user_defined_functions: نادرست
windows_timer_interval: 1
transparent_data_encryption_options:
فعال: نادرست
سنگ قبر_آستانه_هشدار: 1000
سنگ قبر_آستانه_شکست: 100000
batch_size_warn_threshold_in_kb: 200
batch_size_fail_threshold_in_kb: 250
unlogged_batch_across_partitions_warn_threshold: 10
compaction_large_partition_warning_threshold_mb: 100
gc_warn_threshold_in_ms: 1000
back_pressure_enabled: نادرست
enable_materialized_views: درست است
enable_sasi_indexes: درست است

تنظیمات GC:

### تنظیمات CMS-XX:+UseParNewGC
-XX:+UseConcMarkSweepGC
-XX:+CMSParallelRemarkEnabled
-XX:SurvivorRatio=8
-XX:MaxTenuringThreshold=1
-XX:CMSInitiatingOccupancyFraction=75
-XX:+UseCMSInitiatingOccupancyOnly
-XX:CMSWaitDuration=10000
-XX:+CMSParallelInitialMarkEnabled
-XX:+CMSEdenChunksRecordAlways
-XX:+CMSClassUnloadingEnabled

حافظه jvm.options 16 گیگابیت اختصاص داشت (ما 32 گیگابیت را هم امتحان کردیم، تفاوتی مشاهده نشد).

جداول با دستور زیر ایجاد شدند:

CREATE TABLE ks.t1 (id bigint PRIMARY KEY, title text) WITH compression = {'sstable_compression': 'LZ4Compressor', 'chunk_length_kb': 64};

نسخه HB: 1.2.0-cdh5.14.2 (در کلاس org.apache.hadoop.hbase.regionserver.HRegion ما MetricsRegion را حذف کردیم که وقتی تعداد مناطق در RegionServer بیش از 1000 منطقه بود به GC منجر شد)

پارامترهای غیر پیش فرض HBasezookeeper.session.timeout: 120000
hbase.rpc.timeout: 2 دقیقه
hbase.client.scanner.timeout.دوره: 2 دقیقه
hbase.master.handler.count: 10
hbase.regionserver.lease.period، hbase.client.scanner.timeout.period: 2 دقیقه
hbase.regionserver.handler.count: 160
hbase.regionserver.metahandler.count: 30
hbase.regionserver.logroll.period: 4 ساعت
hbase.regionserver.maxlogs: 200
hbase.hregion.memstore.flush.size: 1 گیگابایت
hbase.hregion.memstore.block.multiplier: 6
hbase.hstore.compactionThreshold: 5
hbase.hstore.blockingStoreFiles: 200
hbase.hregion.majorcompaction: 1 روز
قطعه پیکربندی پیشرفته سرویس HBase (دریچه ایمنی) برای hbase-site.xml:
hbase.regionserver.wal.codecorg.apache.hadoop.hbase.regionserver.wal.IndexedWALEditCodec
hbase.master.namespace.init.timeout3600000
hbase.regionserver.optionalcacheflushinterval18000000
hbase.regionserver.thread.compaction.large12
hbase.regionserver.wal.enablecompressiontrue
hbase.hstore.compaction.max.size1073741824
hbase.server.compactchecker.interval.multiplier200
گزینه های پیکربندی جاوا برای HBase RegionServer:
-XX:+UseParNewGC -XX:+UseConcMarkSweepGC -XX:CMSInitiatingOccupancyFraction=70 -XX:+CMSParallelRemarkEnabled -XX:ReservedCodeCacheSize=256m
hbase.snapshot.master.timeoutMillis: 2 دقیقه
hbase.snapshot.region.timeout: 2 دقیقه
hbase.snapshot.master.timeout.millis: 2 دقیقه
حداکثر حجم لاگ سرور HBase REST: 100 مگابایت
حداکثر پشتیبان‌گیری از فایل لاگ سرور HBase REST: 5
حداکثر حجم لاگ سرور HBase Thrift: 100 مگابایت
حداکثر پشتیبان‌گیری از فایل لاگ سرور HBase Thrift: 5
Master Max حجم لاگ: 100 مگابایت
حداکثر پشتیبان‌گیری از فایل لاگ اصلی: 5
حداکثر حجم Log RegionServer: 100 مگابایت
حداکثر پشتیبان‌گیری از فایل Log RegionServer: 5
پنجره تشخیص اصلی HBase Active: 4 دقیقه
dfs.client.hedged.read.threadpool.size: 40
dfs.client.hedged.read.threshold.millis: 10 میلی ثانیه
hbase.rest.threads.min: 8
hbase.rest.threads.max: 150
حداکثر توصیف کننده فایل فرآیند: 180000
hbase.thrift.minWorkerThreads: 200
hbase.master.executor.openregion.threads: 30
hbase.master.executor.closeregion.threads: 30
hbase.master.executor.serverops.threads: 60
hbase.regionserver.thread.compaction.small: 6
hbase.ipc.server.read.threadpool.size: 20
موضوعات انتقال دهنده منطقه: 6
سایز Client Java Heap در بایت: 1 گیگابایت
گروه پیش فرض سرور HBase REST: 3 گیگابایت
گروه پیش فرض سرور HBase Thrift: 3 گیگابایت
Java Heap حجم HBase Master در بایت: 16 گیگابایت
جاوا Heap حجم سرور HBase RegionServer در بایت: 32 گیگابایت

+zooKeeper
maxClientCnxns: 601
maxSessionTimeout: 120000
ایجاد جداول:
hbase org.apache.hadoop.hbase.util.RegionSplitter ns:t1 UniformSplit -c 64 -f cf
تغییر 'ns:t1'، {NAME => 'cf'، DATA_BLOCK_ENCODING => 'FAST_DIFF'، COMPRESSION => 'GZ'}

یک نکته مهم در اینجا وجود دارد - توضیحات DataStax نمی گوید که از چند ناحیه برای ایجاد جداول HB استفاده شده است، اگرچه این برای حجم های زیاد بسیار مهم است. بنابراین، برای آزمایش‌ها، مقدار = 64 انتخاب شد که امکان ذخیره‌سازی تا 640 گیگابایت، یعنی. میز سایز متوسط

در زمان آزمایش، HBase دارای 22 هزار جدول و 67 هزار منطقه بود (اگر پچ ذکر شده در بالا نبود، برای نسخه 1.2.0 کشنده بود).

حالا برای کد. از آنجایی که مشخص نبود کدام پیکربندی برای یک پایگاه داده خاص سودمندتر است، آزمایش ها در ترکیب های مختلف انجام شد. آن ها در برخی آزمایشات، 4 جدول به طور همزمان بارگذاری شد (هر 4 گره برای اتصال استفاده شد). در تست های دیگر با 8 جدول مختلف کار کردیم. در برخی موارد، اندازه دسته 100 و در برخی دیگر 200 بود (پارامتر دسته - کد زیر را ببینید). اندازه داده برای مقدار 10 بایت یا 100 بایت (dataSize) است. در مجموع، هر بار 5 میلیون رکورد در هر جدول نوشته و خوانده شد. در همان زمان، 5 رشته برای هر جدول نوشته شد/خوانده شد (تعداد رشته - thNum) که هر کدام از محدوده کلیدهای خاص خود استفاده کردند (تعداد = 1 میلیون):

if (opType.equals("insert")) {
    for (Long key = count * thNum; key < count * (thNum + 1); key += 0) {
        StringBuilder sb = new StringBuilder("BEGIN BATCH ");
        for (int i = 0; i < batch; i++) {
            String value = RandomStringUtils.random(dataSize, true, true);
            sb.append("INSERT INTO ")
                    .append(tableName)
                    .append("(id, title) ")
                    .append("VALUES (")
                    .append(key)
                    .append(", '")
                    .append(value)
                    .append("');");
            key++;
        }
        sb.append("APPLY BATCH;");
        final String query = sb.toString();
        session.execute(query);
    }
} else {
    for (Long key = count * thNum; key < count * (thNum + 1); key += 0) {
        StringBuilder sb = new StringBuilder("SELECT * FROM ").append(tableName).append(" WHERE id IN (");
        for (int i = 0; i < batch; i++) {
            sb = sb.append(key);
            if (i+1 < batch)
                sb.append(",");
            key++;
        }
        sb = sb.append(");");
        final String query = sb.toString();
        ResultSet rs = session.execute(query);
    }
}

بر این اساس، عملکرد مشابهی برای HB ارائه شد:

Configuration conf = getConf();
HTable table = new HTable(conf, keyspace + ":" + tableName);
table.setAutoFlush(false, false);
List<Get> lGet = new ArrayList<>();
List<Put> lPut = new ArrayList<>();
byte[] cf = Bytes.toBytes("cf");
byte[] qf = Bytes.toBytes("value");
if (opType.equals("insert")) {
    for (Long key = count * thNum; key < count * (thNum + 1); key += 0) {
        lPut.clear();
        for (int i = 0; i < batch; i++) {
            Put p = new Put(makeHbaseRowKey(key));
            String value = RandomStringUtils.random(dataSize, true, true);
            p.addColumn(cf, qf, value.getBytes());
            lPut.add(p);
            key++;
        }
        table.put(lPut);
        table.flushCommits();
    }
} else {
    for (Long key = count * thNum; key < count * (thNum + 1); key += 0) {
        lGet.clear();
        for (int i = 0; i < batch; i++) {
            Get g = new Get(makeHbaseRowKey(key));
            lGet.add(g);
            key++;
        }
        Result[] rs = table.get(lGet);
    }
}

از آنجایی که در HB مشتری باید از توزیع یکنواخت داده ها مراقبت کند، تابع نمکی کلید به شکل زیر است:

public static byte[] makeHbaseRowKey(long key) {
    byte[] nonSaltedRowKey = Bytes.toBytes(key);
    CRC32 crc32 = new CRC32();
    crc32.update(nonSaltedRowKey);
    long crc32Value = crc32.getValue();
    byte[] salt = Arrays.copyOfRange(Bytes.toBytes(crc32Value), 5, 7);
    return ArrayUtils.addAll(salt, nonSaltedRowKey);
}

اکنون جالب ترین بخش - نتایج:

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

همین مورد در شکل نمودار:

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank

مزیت HB آنقدر تعجب آور است که این ظن وجود دارد که نوعی گلوگاه در راه اندازی CS وجود دارد. با این حال، گوگل و جستجو برای مشخص ترین پارامترها (مانند concurrent_writes یا memtable_heap_space_in_mb) سرعت کار را افزایش نداد. در عین حال، سیاهههای مربوط تمیز هستند و به هیچ چیز فحش نمی دهند.

داده ها به طور مساوی در بین گره ها توزیع شد، آمار از همه گره ها تقریباً یکسان بود.

این چیزی است که آمار جدول از یکی از گره ها به نظر می رسدفضای کلید: ks
تعداد خوانده شده: 9383707
تأخیر خواندن: 0.04287025042448576 ms
تعداد نوشتن: 15462012
تأخیر نوشتن: 0.1350068438699957 میلی‌ثانیه
فلاش های معلق: 0
جدول: t1
تعداد SSTable: 16
فضای استفاده شده (زنده): 148.59 مگابایت
فضای استفاده شده (کل): 148.59 مگابایت
فضای استفاده شده توسط عکس های فوری (کل): 0 بایت
حافظه خاموش استفاده شده (مجموع): 5.17 مگابایت
نسبت فشرده سازی SSTable: 0.5720989576459437
تعداد پارتیشن (تخمین): 3970323
تعداد سلول های Memtable: 0
اندازه داده Memtable: 0 بایت
حافظه Memtable off heap استفاده شده: 0 بایت
تعداد سوئیچ Memtable: 5
تعداد خوانده شده محلی: 2346045
تأخیر خواندن محلی: NaN ms
تعداد نوشتار محلی: 3865503
تأخیر نوشتن محلی: NaN ms
فلاش های معلق: 0
درصد تعمیر: 0.0
مثبت کاذب فیلتر بلوم: 25
نسبت کاذب فیلتر بلوم: 0.00000
فضای فیلتر بلوم استفاده شده: 4.57 مگابایت
فیلتر شکن از حافظه پشته استفاده شده: 4.57 مگابایت
خلاصه شاخص حافظه استفاده شده از پشته: 590.02 کیلوبایت
ابرداده فشرده سازی حافظه پشته استفاده شده: 19.45 کیلوبایت
حداقل بایت پارتیشن فشرده: 36
حداکثر بایت پارتیشن فشرده: 42
میانگین بایت پارتیشن فشرده: 42
میانگین سلول های زنده در هر برش (پنج دقیقه آخر): NaN
حداکثر سلول زنده در هر برش (پنج دقیقه آخر): 0
میانگین سنگ قبر در هر برش (پنج دقیقه آخر): NaN
حداکثر سنگ قبر در هر برش (پنج دقیقه آخر): 0
جهش های کاهش یافته: 0 بایت

تلاش برای کاهش اندازه دسته (حتی ارسال آن به صورت جداگانه) تأثیری نداشت، فقط بدتر شد. ممکن است که در واقع این حداکثر عملکرد برای CS باشد، زیرا نتایج به دست آمده برای CS مشابه نتایج بدست آمده برای DataStax است - حدود صدها هزار عملیات در ثانیه. علاوه بر این، اگر به استفاده از منابع نگاه کنیم، خواهیم دید که CS از CPU و دیسک های بسیار بیشتری استفاده می کند:

نبرد دو یاکوزونا یا کاساندرا در مقابل HBase. تجربه تیم Sberbank
شکل، استفاده در طول اجرای تمام تست‌های پشت سر هم برای هر دو پایگاه داده را نشان می‌دهد.

با توجه به مزیت خواندن قدرتمند HB. در اینجا می توانید ببینید که برای هر دو پایگاه داده، استفاده از دیسک در حین خواندن بسیار کم است (تست های خواندن آخرین بخش چرخه آزمایش برای هر پایگاه داده هستند، به عنوان مثال برای CS این از 15:20 تا 15:40 است). در مورد HB، دلیل روشن است - بیشتر داده ها در حافظه، در حافظه ذخیره می شوند، و برخی در حافظه پنهان ذخیره می شوند. در مورد CS، نحوه عملکرد آن خیلی واضح نیست، اما بازیافت دیسک نیز قابل مشاهده نیست، اما در هر صورت، سعی شده است تا کش row_cache_size_in_mb = 2048 فعال شود و caching = {'keys': 'ALL'، تنظیم شود. 'rows_per_partition': '2000000'}، اما این وضعیت را حتی کمی بدتر کرد.

همچنین لازم است یک بار دیگر به یک نکته مهم در مورد تعداد مناطق در HB اشاره شود. در مورد ما، مقدار 64 مشخص شده بود. اگر آن را کاهش دهید و آن را به عنوان مثال 4 برابر کنید، در هنگام خواندن، سرعت 2 برابر کاهش می یابد. دلیل آن این است که memstore سریع‌تر پر می‌شود و فایل‌ها اغلب شستشو می‌شوند و هنگام خواندن، فایل‌های بیشتری باید پردازش شوند، که یک عملیات نسبتاً پیچیده برای HB است. در شرایط واقعی، می توان با فکر کردن از طریق یک استراتژی پیش تقسیم و فشرده سازی این مشکل را درمان کرد؛ به ویژه، ما از یک ابزار خودنویس استفاده می کنیم که زباله ها را جمع آوری می کند و HFiles را به طور مداوم در پس زمینه فشرده می کند. کاملاً ممکن است که برای تست های DataStax آنها فقط 1 منطقه را به هر جدول اختصاص دهند (که صحیح نیست) و این تا حدودی روشن می کند که چرا HB در تست های خواندن آنها بسیار پایین است.

نتایج اولیه زیر از این نتیجه گرفته می شود. با فرض اینکه هیچ اشتباه بزرگی در طول آزمایش انجام نشده است، پس کاساندرا شبیه یک غول بزرگ با پاهای سفالی است. به طور دقیق تر، در حالی که او مانند تصویر ابتدای مقاله روی یک پا تعادل دارد، نتایج نسبتاً خوبی نشان می دهد، اما در یک مبارزه در همان شرایط کاملاً بازنده است. در همان زمان، با در نظر گرفتن استفاده کم از CPU در سخت افزارمان، یاد گرفتیم که دو منطقه سرور HB در هر میزبان نصب کنیم و در نتیجه عملکرد را دو برابر کردیم. آن ها با در نظر گرفتن استفاده از منابع، وضعیت CS حتی اسفناک تر است.

البته این تست‌ها کاملاً مصنوعی هستند و مقدار داده‌هایی که در اینجا استفاده شد نسبتاً کم است. این امکان وجود دارد که اگر به ترابایت تغییر می کردیم، وضعیت متفاوت می شد، اما در حالی که برای HB می توانیم ترابایت را بارگیری کنیم، برای CS این مشکل ساز شد. اغلب حتی با این حجم‌ها یک OperationTimedOutException می‌فرستاد، اگرچه پارامترهای انتظار برای پاسخ قبلاً چندین برابر در مقایسه با پارامترهای پیش‌فرض افزایش یافته بود.

امیدوارم با تلاش مشترک بتوانیم گلوگاه های CS را پیدا کنیم و اگر بتوانیم آن را تسریع کنیم، در پایان پست قطعاً اطلاعاتی در مورد نتایج نهایی اضافه خواهم کرد.

UPD: به لطف توصیه رفقا، توانستم سرعت خواندن را افزایش دهم. بود:
159 عملیات (644 جدول، 4 جریان، دسته 5).
اضافه:
.withLoadBalancingPolicy(New TokenAwarePolicy(DCAwareRoundRobinPolicy.builder().build()))
و من با تعداد نخ ها بازی کردم. نتیجه به شرح زیر است:
4 جدول، 100 رشته، دسته = 1 (قطعه به قطعه): 301 عملیات
4 جدول، 100 رشته، دسته = 10: 447 عملیات
4 جدول، 100 رشته، دسته = 100: 625 عملیات

بعداً سایر نکات تنظیم را اعمال می کنم، یک چرخه کامل تست را اجرا می کنم و نتایج را در انتهای پست اضافه می کنم.

منبع: www.habr.com

اضافه کردن نظر