ควรมี mysql innodb_buffer_pool_size ขนาดเท่าใด


170

ฉันมีฐานข้อมูลไม่ว่างที่มีตาราง InnoDB แต่เพียงผู้เดียวซึ่งมีขนาดประมาณ 5GB ฐานข้อมูลทำงานบนเซิร์ฟเวอร์ Debian โดยใช้ดิสก์ SSD และฉันได้ตั้งค่าการเชื่อมต่อสูงสุด = 800 ซึ่งบางครั้งทำให้อิ่มตัวและบดขยี้เซิร์ฟเวอร์ให้หยุดทำงาน ข้อความค้นหาเฉลี่ยต่อวินาทีประมาณ 2.5K ดังนั้นฉันจำเป็นต้องปรับการใช้หน่วยความจำให้เหมาะสมเพื่อให้มีพื้นที่สำหรับการเชื่อมต่อที่เป็นไปได้สูงสุด

ฉันเห็นคำแนะนำแล้วว่า innodb_buffer_pool_size ควรมีขนาดสูงสุด 80% ของหน่วยความจำทั้งหมด ในอีกทางหนึ่งฉันได้รับคำเตือนจากสคริปต์ปรับแต่งไพรเมอร์:

Max Memory Ever Allocated : 91.97 G
Configured Max Per-thread Buffers : 72.02 G
Configured Max Global Buffers : 19.86 G
Configured Max Memory Limit : 91.88 G
Physical Memory : 94.58 G

นี่คือตัวแปร innodb ปัจจุบันของฉัน:

| innodb_adaptive_flushing                          | ON                                                                                                                     |
| innodb_adaptive_hash_index                        | ON                                                                                                                     |
| innodb_additional_mem_pool_size                   | 20971520                                                                                                               |
| innodb_autoextend_increment                       | 8                                                                                                                      |
| innodb_autoinc_lock_mode                          | 1                                                                                                                      |
| innodb_buffer_pool_instances                      | 1                                                                                                                      |
| innodb_buffer_pool_size                           | 20971520000                                                                                                            |
| innodb_change_buffering                           | all                                                                                                                    |
| innodb_checksums                                  | ON                                                                                                                     |
| innodb_commit_concurrency                         | 0                                                                                                                      |
| innodb_concurrency_tickets                        | 500                                                                                                                    |
| innodb_data_file_path                             | ibdata1:10M:autoextend                                                                                                 |
| innodb_data_home_dir                              |                                                                                                                        |
| innodb_doublewrite                                | ON                                                                                                                     |
| innodb_fast_shutdown                              | 1                                                                                                                      |
| innodb_file_format                                | Antelope                                                                                                               |
| innodb_file_format_check                          | ON                                                                                                                     |
| innodb_file_format_max                            | Antelope                                                                                                               |
| innodb_file_per_table                             | ON                                                                                                                     |
| innodb_flush_log_at_trx_commit                    | 2                                                                                                                      |
| innodb_flush_method                               | O_DIRECT                                                                                                               |
| innodb_force_load_corrupted                       | OFF                                                                                                                    |
| innodb_force_recovery                             | 0                                                                                                                      |
| innodb_io_capacity                                | 200                                                                                                                    |
| innodb_large_prefix                               | OFF                                                                                                                    |
| innodb_lock_wait_timeout                          | 50                                                                                                                     |
| innodb_locks_unsafe_for_binlog                    | OFF                                                                                                                    |
| innodb_log_buffer_size                            | 4194304                                                                                                                |
| innodb_log_file_size                              | 524288000                                                                                                              |
| innodb_log_files_in_group                         | 2                                                                                                                      |
| innodb_log_group_home_dir                         | ./                                                                                                                     |
| innodb_max_dirty_pages_pct                        | 75                                                                                                                     |
| innodb_max_purge_lag                              | 0                                                                                                                      |
| innodb_mirrored_log_groups                        | 1                                                                                                                      |
| innodb_old_blocks_pct                             | 37                                                                                                                     |
| innodb_old_blocks_time                            | 0                                                                                                                      |
| innodb_open_files                                 | 300                                                                                                                    |
| innodb_purge_batch_size                           | 20                                                                                                                     |
| innodb_purge_threads                              | 0                                                                                                                      |
| innodb_random_read_ahead                          | OFF                                                                                                                    |
| innodb_read_ahead_threshold                       | 56                                                                                                                     |
| innodb_read_io_threads                            | 4                                                                                                                      |
| innodb_replication_delay                          | 0                                                                                                                      |
| innodb_rollback_on_timeout                        | OFF                                                                                                                    |
| innodb_rollback_segments                          | 128                                                                                                                    |
| innodb_spin_wait_delay                            | 6                                                                                                                      |
| innodb_stats_method                               | nulls_equal                                                                                                            |
| innodb_stats_on_metadata                          | ON                                                                                                                     |
| innodb_stats_sample_pages                         | 8                                                                                                                      |
| innodb_strict_mode                                | OFF                                                                                                                    |
| innodb_support_xa                                 | ON                                                                                                                     |
| innodb_sync_spin_loops                            | 30                                                                                                                     |
| innodb_table_locks                                | ON                                                                                                                     |
| innodb_thread_concurrency                         | 4                                                                                                                      |
| innodb_thread_sleep_delay                         | 10000                                                                                                                  |
| innodb_use_native_aio                             | ON                                                                                                                     |
| innodb_use_sys_malloc                             | ON                                                                                                                     |
| innodb_version                                    | 1.1.8                                                                                                                  |
| innodb_write_io_threads                           | 4                                                                                                                      |

ข้อความด้านข้างที่อาจเกี่ยวข้อง: ฉันเห็นว่าเมื่อฉันพยายามแทรกโพสต์ขนาดใหญ่ (พูดเกิน 10KB) จาก Drupal (ซึ่งอยู่ในเว็บเซิร์ฟเวอร์แยกต่างหาก) ไปยังฐานข้อมูลมันจะคงอยู่ตลอดไปและหน้าไม่ได้กลับมาอย่างถูกต้อง

เกี่ยวกับสิ่งเหล่านี้ฉันสงสัยว่าสิ่งที่ควรเป็น innodb_buffer_pool_size ของฉันเพื่อประสิทธิภาพที่ดีที่สุด ฉันขอขอบคุณข้อเสนอแนะของคุณเพื่อตั้งค่านี้และพารามิเตอร์อื่น ๆ อย่างเหมาะสมที่สุดสำหรับสถานการณ์นี้

คำตอบ:


252

innodb_buffer_pool_sizeของคุณมีขนาดใหญ่มาก 20971520000คุณได้ตั้งไว้ที่ นั่นคือ 19.5135 GB หากคุณมีข้อมูลและดัชนี InnoDB เพียง 5GB คุณควรมีขนาด 8GB เท่านั้น แม้แต่สิ่งนี้อาจสูงเกินไป

นี่คือสิ่งที่คุณควรทำ เรียกใช้แบบสอบถามนี้ก่อน

SELECT CEILING(Total_InnoDB_Bytes*1.6/POWER(1024,3)) RIBPS FROM
(SELECT SUM(data_length+index_length) Total_InnoDB_Bytes
FROM information_schema.tables WHERE engine='InnoDB') A;

สิ่งนี้จะทำให้ RIBPS, ขนาด InnoDB Buffer Pool ที่แนะนำของคุณอ้างอิงจากข้อมูลและดัชนี InnoDB ทั้งหมดที่เพิ่มขึ้น 60%

ตัวอย่างเช่น

mysql>     SELECT CEILING(Total_InnoDB_Bytes*1.6/POWER(1024,3)) RIBPS FROM
    ->     (SELECT SUM(data_length+index_length) Total_InnoDB_Bytes
    ->     FROM information_schema.tables WHERE engine='InnoDB') A;
+-------+
| RIBPS |
+-------+
|     8 |
+-------+
1 row in set (4.31 sec)

mysql>

ด้วยเอาต์พุตนี้คุณจะตั้งค่าต่อไปนี้ใน /etc/my.cnf

[mysqld]
innodb_buffer_pool_size=8G

ต่อไป, service mysql restart

หลังจากรีสตาร์ทให้รัน mysql เป็นเวลาหนึ่งหรือสองสัปดาห์ จากนั้นเรียกใช้แบบสอบถามนี้:

SELECT (PagesData*PageSize)/POWER(1024,3) DataGB FROM
(SELECT variable_value PagesData
FROM information_schema.global_status
WHERE variable_name='Innodb_buffer_pool_pages_data') A,
(SELECT variable_value PageSize
FROM information_schema.global_status
WHERE variable_name='Innodb_page_size') B;

สิ่งนี้จะช่วยให้คุณทราบถึงจำนวนหน่วยความจำ GB จริงที่ถูกใช้โดย InnoDB Data ใน InnoDB Buffer Pool ในขณะนี้

ฉันเคยเขียนเกี่ยวกับเรื่องนี้มาก่อน: จะตั้ง innodb_buffer_pool ได้อย่างไรและทำไม ..

คุณสามารถเรียกใช้DataGBแบบสอบถามนี้ได้ทันทีแทนที่จะกำหนดค่าใหม่เริ่มต้นใหม่และรอหนึ่งสัปดาห์

ค่านี้DataGBมีความใกล้เคียงกับขนาดของ InnoDB Buffer Pool ที่มีขนาดใหญ่ขึ้น + (เปอร์เซ็นต์ที่ระบุใน innodb_change_buffer_max_size) ฉันแน่ใจว่านี่จะน้อยกว่า 20000M ที่คุณได้จองไว้ตอนนี้ การประหยัด RAM สามารถใช้ในการปรับแต่งสิ่งอื่น ๆ เช่น

ถ้ำ # 1

นี้เป็นสิ่งสำคัญมากที่จะทราบ: ในบางครั้งอาจต้องใช้ InnoDB เพิ่มอีก 10% มากกว่าค่าสำหรับinnodb_buffer_pool_size นี่คือสิ่งที่เอกสาร MySQLกล่าวในที่นี้:

ยิ่งคุณตั้งค่านี้มากขึ้นเท่าไหร่จำเป็นต้องใช้ดิสก์ I / O น้อยกว่าในการเข้าถึงข้อมูลในตาราง บนเซิร์ฟเวอร์ฐานข้อมูลเฉพาะคุณสามารถตั้งค่านี้ได้สูงสุด 80% ของขนาดหน่วยความจำกายภาพของเครื่อง เตรียมพร้อมที่จะลดขนาดของค่านี้หากปัญหาอื่น ๆ เหล่านี้เกิดขึ้น:

การแข่งขันสำหรับหน่วยความจำกายภาพอาจทำให้เกิดการเพจในระบบปฏิบัติการ

InnoDB ขอสงวนหน่วยความจำเพิ่มเติมสำหรับบัฟเฟอร์และโครงสร้างการควบคุมเพื่อให้พื้นที่ที่จัดสรรทั้งหมดมีขนาดใหญ่กว่าขนาดที่ระบุประมาณ 10%

พื้นที่ที่อยู่จะต้องต่อเนื่องกันซึ่งอาจเป็นปัญหาในระบบ Windows ที่มี DLL ที่โหลดตามที่อยู่เฉพาะ

เวลาในการเตรียมใช้งานบัฟเฟอร์พูลนั้นเป็นสัดส่วนกับขนาดโดยประมาณ ในการติดตั้งขนาดใหญ่เวลาเริ่มต้นนี้อาจมีความสำคัญ ตัวอย่างเช่นบนเซิร์ฟเวอร์ Linux x86_64 ที่ทันสมัยการกำหนดค่าเริ่มต้นของพูลบัฟเฟอร์ 10GB ใช้เวลาประมาณ 6 วินาที ดูหัวข้อ 8.9.1, “การ InnoDB บัฟเฟอร์สระว่ายน้ำ”

ถ้ำ # 2

ฉันเห็นค่าต่อไปนี้ในของคุณ my.cnf

| innodb_io_capacity                                | 200 |
| innodb_read_io_threads                            | 4   |
| innodb_thread_concurrency                         | 4   |
| innodb_write_io_threads                           | 4   |

หมายเลขเหล่านี้จะขัดขวาง InnoDB ไม่ให้เข้าถึงหลายคอร์

โปรดตั้งค่าต่อไปนี้:

[mysqld]
innodb_io_capacity = 2000
innodb_read_io_threads = 64
innodb_thread_concurrency = 0
innodb_write_io_threads = 64

ฉันได้เขียนเกี่ยวกับเรื่องนี้มาก่อนใน DBA StackExchange

ฉันเพิ่งตอบคำถามเช่นนี้ใน ServerFault โดยใช้สูตรที่กระชับยิ่งขึ้น :

SELECT CONCAT(CEILING(RIBPS/POWER(1024,pw)),SUBSTR(' KMGT',pw+1,1))
Recommended_InnoDB_Buffer_Pool_Size FROM
(
    SELECT RIBPS,FLOOR(LOG(RIBPS)/LOG(1024)) pw
    FROM
    (
        SELECT SUM(data_length+index_length)*1.1*growth RIBPS
        FROM information_schema.tables AAA,
        (SELECT 1.25 growth) BBB
        WHERE ENGINE='InnoDB'
    ) AA
) A;

1
ขอบคุณสำหรับการโพสต์ที่ยอดเยี่ยมนี้! สูตรของคุณที่ขึ้นต้นด้วยSELECT (PagesData*PageSize)/POWER(1024,3) DataGB FROM...สร้างข้อผิดพลาดต่อไปนี้ใน MySQL 5.7: " ฟีเจอร์ 'INFORMATION_SCHEMA.GLOBAL_STATUS' ถูกปิดใช้งานดูที่เอกสารประกอบสำหรับ 'show_compatibility_56' " คุณมีรุ่นที่ได้รับการปรับปรุงโดยบังเอิญหรือไม่?
Benjamin

ฉันได้รับ 307 RIBPS และ 264G นั่นหมายความว่าฉันต้องการ RAM 307GB ใช่ไหม
E_Blue

264G ขึ้นไป แต่คุณควรมี RAM เพียงพอสำหรับสิ่งนั้นมิฉะนั้นให้ 80% ของ RAM ของคุณกับ mysql ขึ้นอยู่กับสิ่งอื่นที่ทำงานบนระบบ
sjas

2
โพสต์ที่ยิ่งใหญ่ที่สุดที่ฉันเคยอ่าน! ฉันมีฐานข้อมูลขนาดใหญ่ประมาณ 3GB หลังจากอ่านคำตอบ / บทความของคุณแล้วความเร็วในการเชื่อมโยงจะเพิ่มขึ้นถึง 2x
fat_mike

4
@Benjamin: ในฐานะของ MySQL 5.7.6 data_schema ถูกรวมเข้ากับ performance_schema ดังนั้นเพียงแค่เปลี่ยน "information_schema" เป็น "performance_schema" ในแบบสอบถามเพื่อให้ทำงานได้ ที่มา: dev.mysql.com/doc/refman/5.7/en/status-table.html
Ralph Bolton

11

อะไรแบบนี้? การใช้SHOW VARIABLESและSHOW GLOBAL STATUS:

นิพจน์: innodb_buffer_pool_size / _ram
ความหมาย: % ของ RAM ที่ใช้สำหรับ InnoDB buffer_pool
ช่วงที่แนะนำ: 60 ~ 80%

นิพจน์: Innodb_buffer_pool_reads / Innodb_buffer_pool_read_requests
ความหมาย: อ่านคำขอที่มีการเข้าชมดิสก์
ช่วงที่แนะนำ: 0-2%
จะทำอย่างไรถ้านอกช่วง: เพิ่ม innodb_buffer_pool_size แกะ.

นิพจน์: Innodb_pages_read / Innodb_buffer_pool_read_requests
ความหมาย: คำขอการอ่านที่ต้องใช้ดิสก์
ช่วงที่แนะนำ: 0-2%
จะทำอย่างไรถ้าอยู่นอกช่วง: เพิ่ม innodb_buffer_pool_size ถ้าคุณมี RAM เพียงพอ

นิพจน์: Innodb_pages_written / Innodb_buffer_pool_write_requests
ความหมาย: คำขอการเขียนที่ต้องกดดิสก์
ช่วงที่แนะนำ: 0-15%
จะทำอย่างไรถ้าอยู่นอกช่วง: ตรวจสอบ innodb_buffer_pool_size

นิพจน์: Innodb_buffer_pool_reads / Uptime
ความหมาย: อ่าน
ช่วงที่แนะนำ: 0-100 / วินาที
จะทำอย่างไรถ้าอยู่นอกช่วง: เพิ่ม innodb_buffer_pool_size?

นิพจน์: (Innodb_buffer_pool_reads + Innodb_buffer_pool_pages_flushed) / Uptime
ความหมาย: InnoDB I / O
ช่วงที่แนะนำ: 0-100 / วินาที
จะทำอย่างไรถ้าอยู่นอกช่วง: เพิ่ม innodb_buffer_pool_size?

นิพจน์: Innodb_buffer_pool_pages_flushed / Uptime
ความหมาย: เขียน (วูบวาบ)
ช่วงที่แนะนำ: 0-100 / วินาที
จะทำอย่างไรถ้าอยู่นอกช่วง: เพิ่ม innodb_buffer_pool_size?

นิพจน์: Innodb_buffer_pool_wait_free / Uptime
ความหมาย: ตัว นับเมื่อไม่มีเพจว่างใน buffer_pool นั่นคือทุกหน้าสกปรก
ช่วงที่แนะนำ: 0-1 / วินาที
จะทำอย่างไรถ้าอยู่นอกช่วง: อันดับแรกต้องแน่ใจว่า innodb_buffer_pool_size ตั้งค่าอย่างสมเหตุสมผล หากยังคงมีปัญหาอยู่ให้ลด innodb_max_dirty_pages_pct


ขอบคุณ @Rick สำหรับความคิดเห็นที่ดี innodb_buffer_pool_sizeค่าอะไรระบุ? ขนาดจริงหรือกำหนดค่าหรือไม่
โจ๊ก

1
@joker - innodb_buffer_pool_sizeระบุขนาดสูงสุด ในเซิร์ฟเวอร์ทั่วไป "พูลบัฟเฟอร์" เริ่มต้นเล็ก แต่เติบโตอย่างรวดเร็วจนถึงขนาดสูงสุดและยังคงอยู่ที่นั่น หมายเหตุ: ถ้ามันใหญ่กว่า RAM (หรือปิด) นั่นจะนำไปสู่การแลกเปลี่ยนซึ่งเป็นเรื่องที่แย่มากสำหรับประสิทธิภาพ
Rick James

7

ชื่อของคุณถามเกี่ยวกับ innodb_buffer_pool_size แต่ฉันสงสัยว่าไม่ใช่ปัญหาจริง (Rolando แสดงความคิดเห็นเกี่ยวกับสาเหตุที่คุณตั้งให้ใหญ่พอแม้แต่ใหญ่เกินไป)

ฉันได้ตั้งค่าการเชื่อมต่อสูงสุด = 800 ซึ่งบางครั้งทำให้อิ่มตัวและบดเซิร์ฟเวอร์เพื่อหยุด

นั่นไม่ชัดเจน ผู้ใช้ 800 คนในโหมด "สลีป" มีผลกระทบแทบเป็นศูนย์ต่อระบบ 800 กระทู้ที่ใช้งานจะเป็นภัยพิบัติ หัวข้อ "กำลังทำงาน" มีกี่หัวข้อ

มีการบล็อกเธรดซึ่งกันและกันหรือไม่? ดูสถานะ INNODB เครื่องยนต์แสดงให้เห็นถึงเบาะแสบางอย่างเกี่ยวกับการหยุดชะงัก ฯลฯ

มีคำถามใด ๆ ปรากฏขึ้นในบล็อกที่ช้าหรือไม่? ลองเพิ่มประสิทธิภาพพวกเขา

คุณใช้เวอร์ชั่นอะไร XtraDB (การแทนที่แบบดรอปอินสำหรับ InnoDB) ทำงานได้ดีกว่าในการใช้หลายคอร์ 5.6.7 ทำงานได้ดียิ่งขึ้น

innodb_buffer_pool_instances - เปลี่ยนเป็น 8 (สมมติว่า 20G buffer_pool) มันจะลดลงเล็กน้อยในการแข่งขัน Mutex

คุณเป็น I / O ที่ถูกผูกไว้หรือ CPU ของคุณถูกผูกไว้? การแก้ปัญหานั้นแตกต่างกันอย่างสิ้นเชิงขึ้นอยู่กับคำตอบของคุณ

SSD - มันอาจจะดีกว่าถ้าไฟล์บันทึกทั้งหมดอยู่ในไดรฟ์ที่ไม่ใช่ SSD


6

หน่วยความจำเพิ่มเติมดีกว่าเสมอ แต่จากประสบการณ์ของฉันส่วนใหญ่ขนาดบัฟเฟอร์พูลไม่ควรพอดีกับขนาดข้อมูลของคุณ ตารางส่วนใหญ่ไม่ได้ใช้งานเกือบทุกครั้งเช่นตารางสำรองที่วางอยู่รอบ ๆ ดังนั้นขนาดพูลบัฟเฟอร์ของ Innodb จึงควรจะพอดีกับขนาดข้อมูล acive ของคุณ

กรอบเวลาที่คุณระบุสำหรับเพจที่แอ็คทีฟมีผลต่อประสิทธิภาพ แต่มีจุดที่เหมาะสมซึ่งคุณจะไม่ได้รับประสิทธิภาพที่มากขึ้นสำหรับขนาดบัฟเฟอร์ที่ใหญ่กว่า คุณสามารถประมาณ / คำนวณ / วัดที่โดยshow engine innodb status

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.