Điểm:0

MySQL "Không thể phân bổ bộ nhớ cho vùng đệm" với mức sử dụng bộ nhớ 73%?

lá cờ in

Tôi đang lưu trữ một trang web WordPress trên một giọt DigitalOcean (RAM 1GB). Cơ sở dữ liệu MySQL của trang web thỉnh thoảng gặp sự cố, khiến trang web hiển thị "Lỗi thiết lập kết nối cơ sở dữ liệu". Mức sử dụng bộ nhớ giảm vào khoảng 2:40 sáng, cho biết đây là lúc cơ sở dữ liệu gặp sự cố. Tôi đã kiểm tra tệp nhật ký MySQL cho ngày hôm đó và mục nhập sớm nhất là lúc 10:47 sáng. Đây là phần đầu của tệp nhật ký:

2021-12-06T10:47:14.800977Z 0 [Cảnh báo] DẤU THỜI GIAN với giá trị MẶC ĐỊNH ẩn không được dùng nữa. Vui lòng sử dụng --explicit_defaults_for_timest$
2021-12-06T10:47:14.806192Z 0 [Lưu ý] /usr/sbin/mysqld (mysqld 5.7.36-0ubuntu0.18.04.1) bắt đầu từ quy trình 2810 ...
2021-12-06T10:47:14.819674Z 0 [Lưu ý] InnoDB: hỗ trợ PUNCH HOLE khả dụng
2021-12-06T10:47:14.819711Z 0 [Lưu ý] InnoDB: Mutexes và rw_locks sử dụng nội trang nguyên tử GCC
2021-12-06T10:47:14.819716Z 0 [Lưu ý] InnoDB: Sử dụng các mutex sự kiện
2021-12-06T10:47:14.819720Z 0 [Lưu ý] InnoDB: GCC dựng sẵn __atomic_thread_fence() được sử dụng cho hàng rào bộ nhớ
2021-12-06T10:47:14.819723Z 0 [Lưu ý] InnoDB: Bảng nén sử dụng zlib 1.2.11
2021-12-06T10:47:14.819727Z 0 [Lưu ý] InnoDB: Sử dụng AIO gốc của Linux
2021-12-06T10:47:14.820551Z 0 [Lưu ý] InnoDB: Số nhóm: 1
2021-12-06T10:47:14.823342Z 0 [Lưu ý] InnoDB: Sử dụng hướng dẫn CPU crc32
2021-12-06T10:47:14.825847Z 0 [Lưu ý] InnoDB: Đang khởi tạo nhóm bộ đệm, tổng kích thước = 128M, phiên bản = 1, kích thước khối = 128M
2021-12-06T10:47:14.826246Z 0 [ERROR] InnoDB: mmap(137428992 byte) không thành công; lỗi 12
2021-12-06T10:47:14.826258Z 0 [ERROR] InnoDB: Không thể phân bổ bộ nhớ cho vùng đệm
2021-12-06T10:47:14.826262Z 0 [ERROR] InnoDB: Quá trình khởi tạo plugin bị hủy bỏ do lỗi Lỗi chung
2021-12-06T10:47:14.826270Z 0 [ERROR] Chức năng khởi tạo plugin 'InnoDB' trả về lỗi.
2021-12-06T10:47:14.826274Z 0 [ERROR] Đăng ký plugin 'InnoDB' làm CÔNG CỤ LƯU TRỮ không thành công.
2021-12-06T10:47:14.826278Z 0 [ERROR] Không thể khởi chạy plugin dựng sẵn.
2021-12-06T10:47:14.826282Z 0 [ERROR] Đang hủy bỏ

2021-12-06T10:47:14.832237Z 0 [Chú ý] Kết thúc Binlog
2021-12-06T10:47:14.832297Z 0 [Lưu ý] Tắt plugin 'CSV'
2021-12-06T10:47:14.832572Z 0 [Lưu ý] /usr/sbin/mysqld: Tắt máy hoàn tất

Dựa trên tệp nhật ký, có vẻ như MySQL sắp hết bộ nhớ. Tuy nhiên, mức sử dụng bộ nhớ cho giọt ổn định khoảng 73%, cho đến khi cơ sở dữ liệu gặp sự cố vào khoảng 2:40 sáng, khi đó nó giảm xuống còn 32%. Nó dường như có rất nhiều bộ nhớ, vậy tại sao nó bị sập?

CHỈNH SỬA Theo yêu cầu, đây là nội dung của các tệp cấu hình MySQL của tôi:

/etc/mysql/conf.d/mysql.cnf

[mysql]

/etc/mysql/conf.d/mysqldump.cnf

[mysqldump]
nhanh
trích dẫn tên
max_allowed_packet = 16M

/etc/mysql/mysql.conf.d/mysqld.cnf

#
# Tệp cấu hình máy chủ cơ sở dữ liệu MySQL.
#
# Bạn có thể sao chép cái này vào một trong:
# - "/etc/mysql/my.cnf" để đặt các tùy chọn chung,
# - "~/.my.cnf" để đặt các tùy chọn dành riêng cho người dùng.
#
# Người ta có thể sử dụng tất cả các tùy chọn dài mà chương trình hỗ trợ.
# Chạy chương trình với --help để nhận danh sách các tùy chọn có sẵn và với
# --print-defaults để xem nó thực sự hiểu và sử dụng cái nào.
#
# Để biết giải thích, hãy xem
# http://dev.mysql.com/doc/mysql/en/server-system-variables.html

# Điều này sẽ được chuyển đến tất cả các máy khách mysql
# Đã có báo cáo rằng mật khẩu nên được đặt trong dấu tích/dấu ngoặc kép
# đặc biệt nếu chúng chứa ký tự "#"...
# Nhớ chỉnh sửa /etc/mysql/debian.cnf khi thay đổi vị trí ổ cắm.

# Đây là mục nhập cho một số chương trình cụ thể
# Các giá trị sau giả sử bạn có ít nhất 32M ram

[mysqld_safe]
ổ cắm = /var/run/mysqld/mysqld.sock
đẹp = 0

[mysqld]
#
# * Cài đặt cơ bản
#
người dùng = mysql
tệp pid = /var/run/mysqld/mysqld.pid
ổ cắm = /var/run/mysqld/mysqld.sock
cổng = 3306
dựa trên = /usr
datadir = /var/lib/mysql
tmpdir = /tmp
lc-messages-dir = /usr/share/mysql
bỏ qua khóa ngoài
#
# Thay vì bỏ qua kết nối mạng, mặc định hiện chỉ nghe trên
# localhost tương thích hơn và không kém an toàn hơn.
địa chỉ liên kết = 127.0.0.1
#
# * Tinh chỉnh
#
key_buffer_size = 16M
max_allowed_packet = 16M
thread_stack = 192K
thread_cache_size = 8
# Điều này thay thế tập lệnh khởi động và kiểm tra các bảng MyISAM nếu cần
# lần đầu tiên họ được chạm vào
myisam-recover-options = SAO LƯU
#max_connections = 100
#table_open_cache = 64
#thread_concurrency = 10
#
# * Cấu hình bộ đệm truy vấn
#
query_cache_limit = 1M
truy vấn_cache_size = 16M
#
# * Ghi nhật ký và sao chép
#
# Cả hai vị trí được xoay bởi cronjob.
# Xin lưu ý rằng loại nhật ký này là kẻ giết người hiệu suất.
# Kể từ phiên bản 5.1, bạn có thể kích hoạt nhật ký khi chạy!
#General_log_file = /var/log/mysql/mysql.log
#chung_log = 1
#
# Nhật ký lỗi - nên có rất ít mục.
#
log_error = /var/log/mysql/error.log
#
# Tại đây bạn có thể thấy các truy vấn có thời lượng đặc biệt dài
#slow_query_log = 1
#slow_query_log_file = /var/log/mysql/mysql-slow.log
#long_query_time = 2
#truy vấn nhật ký không sử dụng chỉ mục
#
# Những điều sau đây có thể được sử dụng để dễ dàng phát lại các bản ghi sao lưu hoặc để sao chép.
# lưu ý: nếu bạn đang thiết lập một nô lệ sao chép, hãy xem README.Debian về
# cài đặt khác mà bạn có thể cần phải thay đổi.
# máy chủ-id = 1
#log_bin = /var/log/mysql/mysql-bin.log
hết hạn_logs_ngày = 10
max_binlog_size = 100M
#binlog_do_db = include_database_name
#binlog_ignore_db = include_database_name
#
# * InnoDB
#
# InnoDB được bật theo mặc định với tệp dữ liệu 10 MB trong /var/lib/mysql/.
# Đọc hướng dẫn để biết thêm các tùy chọn liên quan đến InnoDB. Có nhiều!
#
# * Tính năng bảo mật
#
# Đọc hướng dẫn, nếu bạn muốn chroot!
# chroot = /var/lib/mysql/
#
# Để tạo chứng chỉ SSL, tôi khuyên dùng GUI OpenSSL "tinyca".
#
# ssl-ca=/etc/mysql/cacert.pem
# ssl-cert=/etc/mysql/server-cert.pem
# ssl-key=/etc/mysql/server-key.pem

/etc/mysql/mysql.conf.d/mysqld_safe_syslog.cnf

[mysqld_safe]
nhật ký hệ thống
dominix avatar
lá cờ gf
bạn nên có một số cài đặt biến trong /etc/my.cnf.d/server.cnf liên quan đến bộ nhớ và/hoặc innodb không phù hợp với kích thước hoặc bộ nhớ cơ sở dữ liệu của bạn. bạn có thể chỉ cho chúng tôi các biến này và kích thước cơ sở dữ liệu của bạn không?
bumbleshoot avatar
lá cờ in
@dominix Không có thư mục hoặc tệp /etc/my.cnf.d/server.cnf. Thứ gần nhất tôi có thể tìm thấy là /etc/mysql/mysql.conf.d/mysqld.cnf. Máy chủ đang chạy Ubuntu 18.04, nếu điều đó có ích.
lá cờ us
Bạn có thể thêm một đoạn mã dài hơn của tệp nhật ký vào câu hỏi không? Tệp nhật ký này có vẻ như máy chủ MySQL mới khởi động, không khớp với mô tả của bạn.
bumbleshoot avatar
lá cờ in
@dominix Kích thước cơ sở dữ liệu là 43,5 MB.
bumbleshoot avatar
lá cờ in
@TeroKilkanen Theo lịch sử sử dụng bộ nhớ, có vẻ như cơ sở dữ liệu bị lỗi vào khoảng 2:40 sáng. Tuy nhiên, tệp nhật ký cho ngày hôm đó không có mục nào trước 10:47 sáng. Đây là lần gần nhất tôi có thể nhận được vào thời điểm xảy ra sự cố cơ sở dữ liệu. Tôi sẽ mở rộng câu hỏi của mình để bao gồm tất cả các mục từ đầu tệp nhật ký.
lá cờ us
Bạn đã kiểm tra các tệp nhật ký đã xoay chưa?
bumbleshoot avatar
lá cờ in
@TeroKilkanen Tôi đã cập nhật từ ngữ trong câu hỏi của mình, hy vọng bây giờ nó rõ ràng hơn.
bumbleshoot avatar
lá cờ in
@TeroKilkanen Ý bạn là các tệp nhật ký được nén trong/var/log/mysql? Vâng, tôi đã giải nén chúng và đọc chúng.
lá cờ us
`/var/log/kern.log` có bất cứ điều gì xung quanh thời điểm xảy ra sự cố không?
bumbleshoot avatar
lá cờ in
Hãy để chúng tôi [tiếp tục cuộc thảo luận này trong cuộc trò chuyện](https://chat.stackexchange.com/rooms/132261/discussion-between-bumbleshoot-and-tero-kilkanen).
Điểm:2
lá cờ us

Sau khi xem xét nhật ký kernel trong cuộc trò chuyện, lý do khiến MySQL gặp sự cố là do hết bộ nhớ.

Ngày 6 tháng 12 02:47:13 kernel: [341799.228400] Hết bộ nhớ: Giết tiến trình 23566 (mysqld) đạt điểm 197 hoặc hy sinh con
Ngày 6 tháng 12 02:47:13 kernel: [341799.229866] Killed process 23566 (mysqld) total-vm:1168576kB, anon-rss:198536kB, file-rss:0kB, shmem-rss:0kB

Trong thời gian đó, có rất nhiều quy trình Apache2 đang hoạt động. Điều này có nghĩa là lưu lượng truy cập tăng sẽ làm tăng mức tiêu thụ bộ nhớ. Kết quả là kernel quyết định kill MySQL để giải phóng bộ nhớ.

Một người có thể chạy mysqltuner để phân tích cấu hình MySQL. Nó đưa ra các khuyến nghị, có thể giúp giảm mức tiêu thụ bộ nhớ của MySQL.

Tuy nhiên, lưu lượng truy cập ngày càng tăng vẫn có thể gây ra các vấn đề tương tự. Do đó, giải pháp bền vững hơn là tăng bộ nhớ khả dụng cho giọt.

bumbleshoot avatar
lá cờ in
Cảm ơn một lần nữa vì sự giúp đỡ của bạn!
bumbleshoot avatar
lá cờ in
Tôi vừa kiểm tra Google Analytics cho trang web này và chỉ có một lượt xem trang vào ngày 6 tháng 12 (trang web ngừng hoạt động vào ngày 6 tháng 12 trong khoảng thời gian từ 2:40-2:50 sáng). Điều này dường như không khớp với những gì bạn thấy trong nhật ký hạt nhân. Bất cứ ý tưởng tại sao?
lá cờ us
Google Analytics chỉ hiển thị lưu lượng truy cập từ các trình duyệt web thực thi mã Google Analytics JS. Ngoài ra, internet có rất nhiều lưu lượng bot. Bạn có thể thấy lưu lượng truy cập đó trong access.log của máy chủ web của mình
bumbleshoot avatar
lá cờ in
Được rồi, có ý nghĩa. Phải có rất nhiều lưu lượng truy cập bot cùng một lúc để áp đảo một máy chủ luôn chỉ sử dụng 73% bộ nhớ? Bạn có nghĩ rằng đó là một cuộc tấn công DDoS? Có cách nào để chặn lưu lượng bot này trong tương lai không?
Điểm:1
lá cờ ua

1GB RAM là rất nhỏ những ngày này. máy chủ có thể tồn tại nếu bạn thiết lập innodb_buffer_pool_size = 50M. Khuyến nghị về một số phần trăm RAM không áp dụng cho kích thước RAM nhỏ như vậy.

Có rủi ro là 50M sẽ quá nhỏ. vui lòng cung cấp của bạn my.cnf để chúng tôi có thể tìm kiếm các cài đặt khác để thu nhỏ. Một số khả năng:

max_connections = 10
key_buffer_size = 10M
temp_table_size = 10M
max_heap_table_size = 10 triệu
table_open_cache = 100

truy vấn_cache_size = 0
max_allowed_packet = 8M
key_buffer_size = 10M
max_connections = 10

Có, MySQL/MariaDB sẽ chạy trong một cỗ máy nhỏ, nhưng việc điều chỉnh là cần thiết.

Nếu Apache đang chạy trên cùng một máy chủ, hãy hạ MaxRequestWorkers của nó xuống 10. Và kiểm tra cấu hình của bất kỳ thứ gì khác đang chạy trong cùng một máy chủ [ảo].

bumbleshoot avatar
lá cờ in
Cảm ơn vì đã trả lời.`my.cnf` chỉ chứa `!includedir /etc/mysql/conf.d/` và `!includedir /etc/mysql/mysql.conf.d/`. `/etc/mysql/conf.d/` chứa `mysql.cnf` và `mysqldump.cnf`. `/etc/mysql/mysql.conf.d/` chứa `mysqld.cnf` và `mysqld_safe_syslog.cnf`. Bạn có cần xem nội dung của bất kỳ tệp nào trong số này không?
lá cờ ua
@bumbleshoot - Vâng, hãy cho họ xem.
bumbleshoot avatar
lá cờ in
Ok, tôi đã thêm chúng vào câu hỏi ban đầu của mình.
lá cờ ua
@bumbleshoot - Tôi đã thêm một số cài đặt khác để thay đổi.
bumbleshoot avatar
lá cờ in
Cám ơn rất nhiều! Tôi sẽ thử các cài đặt này.

Đăng câu trả lời

Hầu hết mọi người không hiểu rằng việc đặt nhiều câu hỏi sẽ mở ra cơ hội học hỏi và cải thiện mối quan hệ giữa các cá nhân. Ví dụ, trong các nghiên cứu của Alison, mặc dù mọi người có thể nhớ chính xác có bao nhiêu câu hỏi đã được đặt ra trong các cuộc trò chuyện của họ, nhưng họ không trực giác nhận ra mối liên hệ giữa câu hỏi và sự yêu thích. Qua bốn nghiên cứu, trong đó những người tham gia tự tham gia vào các cuộc trò chuyện hoặc đọc bản ghi lại các cuộc trò chuyện của người khác, mọi người có xu hướng không nhận ra rằng việc đặt câu hỏi sẽ ảnh hưởng—hoặc đã ảnh hưởng—mức độ thân thiện giữa những người đối thoại.