कई सिस्टम प्रशासक आमतौर पर चल रहे डेटाबेस कॉन्फ़िगरेशन ट्यूनिंग के महत्व को अनदेखा करते हैं। कॉन्फ़िगरेशन विकल्पों को अक्सर एक बार कॉन्फ़िगर या ट्यून किया जाता है, स्थापना चरण के दौरान, और तब तक छोड़ दिया जाता है जब तक कि डेटाबेस सेवा में कुछ अवांछित घटनाएं नहीं होती हैं। तभी, कोई कॉन्फ़िगरेशन विकल्पों पर फिर से जाने पर अधिक ध्यान देगा और डेटाबेस सेवा को फिर से बहाल करने के लिए सीमाओं, थ्रेशोल्ड, बफ़र्स, कैश आदि को ट्यून करेगा।
इस ब्लॉग पोस्ट में हमारा ध्यान डेटाबेस कॉन्फ़िगरेशन जांच और सत्यापन प्रक्रिया को स्वचालित करना है। यह एक महत्वपूर्ण प्रक्रिया है क्योंकि कॉन्फ़िगरेशन विकल्प हमेशा प्रमुख संस्करणों में बदलते रहते हैं। एक अपरिवर्तित कॉन्फ़िगरेशन फ़ाइल में संभावित रूप से बहिष्कृत विकल्प हो सकते हैं जो अब नए सर्वर संस्करण द्वारा समर्थित नहीं हैं, जो आमतौर पर अपग्रेड किए गए सर्वर के लिए कुछ प्रमुख मुद्दों का कारण बनता है।
कॉन्फ़िगरेशन प्रबंधन उपकरण
कठपुतली, Ansible, शेफ और साल्टस्टैक का उपयोग आमतौर पर DevOps द्वारा कॉन्फ़िगरेशन प्रबंधन और स्वचालन के लिए किया जाता है। कॉन्फ़िगरेशन प्रबंधन उपयोगकर्ताओं को पर्यावरण का दस्तावेजीकरण करने, दक्षता में सुधार, प्रबंधन क्षमता और प्रतिलिपि प्रस्तुत करने योग्यता, और निरंतर एकीकरण और परिनियोजन का एक अभिन्न अंग की अनुमति देता है। अधिकांश कॉन्फ़िगरेशन प्रबंधन उपकरण दूसरों के योगदान के लिए मॉड्यूल और रिपॉजिटरी की एक सूची प्रदान करते हैं, समुदाय उपयोगकर्ता के लिए प्रौद्योगिकी के अनुकूल होने के लिए सीखने की अवस्था को सरल बनाते हैं।
हालांकि कॉन्फ़िगरेशन प्रबंधन टूल का उपयोग अधिकतर परिनियोजन और स्थापना को स्वचालित करने के लिए किया जाता है, हम एक केंद्रीकृत पुश-आउट दृष्टिकोण में कॉन्फ़िगरेशन जांच और प्रवर्तन भी कर सकते हैं। इनमें से प्रत्येक उपकरण का कॉन्फ़िगरेशन फ़ाइल को टेम्प्लेट करने का अपना तरीका है। कठपुतली के लिए, टेम्प्लेट फ़ाइल आमतौर पर ".erb" से जुड़ी होती है और इसके अंदर, हम पूर्व-निर्मित मानों के साथ कॉन्फ़िगरेशन विकल्पों को एक साथ परिभाषित कर सकते हैं।
निम्न उदाहरण MySQL कॉन्फ़िगरेशन के लिए एक टेम्पलेट फ़ाइल दिखाता है:
[mysqld]
thread_concurrency = <%= processorcount.to_i * 2 %>
# Replication
log-bin = /var/lib/mysql/mysql-bin.log
log-bin-index = /var/lib/mysql/mysql-bin.index
binlog_format = mixed
server-id = <%= @mysql_server_id or 1 %>
# InnoDB
innodb_buffer_pool_size = <%= (memorysizeinbytes.to_i / 2 / 1024 / 1024).to_i -%>M
innodb_log_file_size = <%= ((memorysizeinbytes.to_i / 2 / 1024 / 1024) * 0.25).to_i -%>M
जैसा कि ऊपर दिखाया गया है, कॉन्फ़िगरेशन मान एक निश्चित मान या गतिशील रूप से परिकलित हो सकता है। इसलिए, अन्य पूर्वनिर्धारित चर के साथ लक्ष्य होस्ट के हार्डवेयर विनिर्देश के अनुसार अंतिम परिणाम भिन्न हो सकता है। कठपुतली परिभाषा फ़ाइल में, हम अपने कॉन्फ़िगरेशन टेम्पलेट को इस तरह पुश कर सकते हैं:
# Apply our custom template
file { '/etc/mysql/conf.d/my-custom-config.cnf':
ensure => file,
content => template('mysql/my-custom-config.cnf.erb')
}
टेम्पलेट करने के अलावा, हम कॉन्फ़िगरेशन मानों को सीधे परिभाषा फ़ाइल से भी पुश कर सकते हैं। कठपुतली MySQL मॉड्यूल का उपयोग करके मारियाडीबी 10.5 कॉन्फ़िगरेशन के लिए कठपुतली परिभाषा का एक उदाहरण निम्नलिखित है:
# MariaDB configuration
class {'::mysql::server':
package_name => 'mariadb-server',
service_name => 'mariadb',
root_password => 't5[sb^D[+rt8bBYu',
manage_config_file => true,
override_options => {
mysqld => {
'bind_address' => '127.0.0.1',
'max_connections' => '500',
'log_error' => '/var/log/mysql/mariadb.log',
'pid_file' => '/var/run/mysqld/mysqld.pid',
},
mysqld_safe => {
'log_error' => '/var/log/mysql/mariadb.log',
},
}
}
उपरोक्त उदाहरण से पता चलता है कि हमने अपनी कॉन्फ़िगरेशन लाइनों को संरचित करने के लिए manage_config_file => true का उपयोग ओवरराइड_ऑप्शन के साथ किया था जिसे बाद में कठपुतली द्वारा बाहर धकेल दिया जाएगा। मेनिफेस्ट फ़ाइल में कोई भी संशोधन केवल लक्ष्य MySQL कॉन्फ़िगरेशन फ़ाइल की सामग्री को प्रतिबिंबित करेगा। यह मॉड्यूल न तो कॉन्फ़िगरेशन को रनटाइम में लोड करेगा और न ही कॉन्फ़िगरेशन फ़ाइल में परिवर्तनों को पुश करने के बाद MySQL सेवा को पुनरारंभ करेगा। परिवर्तनों को सक्रिय करने के लिए सेवा को फिर से शुरू करना SysAdmin की जिम्मेदारी है।
कठपुतली और रसोइया के लिए, एजेंट लॉग के आउटपुट की जांच करके देखें कि कॉन्फ़िगरेशन विकल्प सही किए गए हैं या नहीं। Ansible के लिए, यह देखने के लिए कि बधाई सफलतापूर्वक अपडेट की गई है या नहीं, डिबगिंग आउटपुट को देखें। कॉन्फ़िगरेशन प्रबंधन टूल का उपयोग करने से आपको कॉन्फ़िगरेशन जांच को स्वचालित करने और केंद्रीकृत कॉन्फ़िगरेशन दृष्टिकोण लागू करने में मदद मिल सकती है।
MySQL शेल
कोई भी अपग्रेड करने से पहले एक विवेक जांच महत्वपूर्ण है। MySQL शेल में एक बहुत अच्छी सुविधा है जिसका उद्देश्य यह सत्यापित करने के लिए परीक्षणों की एक श्रृंखला चलाना है कि क्या आपका मौजूदा इंस्टॉलेशन MySQL 8.0 में अपग्रेड करने के लिए सुरक्षित है, जिसे अपग्रेड चेकर यूटिलिटी कहा जाता है। अपग्रेड की तैयारी करते समय आप काफी समय बचा सकते हैं। एक प्रमुख अपग्रेड, विशेष रूप से MySQL 8.0 के लिए, कई कॉन्फ़िगरेशन विकल्पों का परिचय देता है और उन्हें हटा देता है और इसलिए अपग्रेड के बाद असंगति के लिए एक बड़ा जोखिम होता है।
यह टूल विशेष रूप से MySQL (Percona Server शामिल) के लिए डिज़ाइन किया गया है, खासकर जब आप MySQL 5.7 से MySQL 8.0 में एक बड़ा अपग्रेड करना चाहते हैं। इस उपयोगिता को लागू करने के लिए, MySQL शेल से कनेक्ट करें, और रूट उपयोगकर्ता के रूप में, क्रेडेंशियल, लक्ष्य संस्करण और कॉन्फ़िगरेशन फ़ाइल निर्दिष्ट करें:
$ mysqlsh
mysql> util.checkForServerUpgrade('[email protected]:3306', {"password":"p4ssw0rd", "targetVersion":"8.0.11", "configPath":"/etc/my.cnf"})
रिपोर्ट के निचले भाग में, आपको मुख्य सारांश मिलेगा:
Errors: 7
Warnings: 36
Notices: 0
7 errors were found. Please correct these issues before upgrading to avoid compatibility issues.
पहले सभी त्रुटियों को ठीक करने पर ध्यान दें, क्योंकि यदि कोई कार्रवाई नहीं की जाती है तो यह अपग्रेड के बाद बड़ी समस्याएं पैदा करने वाला है। जनरेट की गई रिपोर्ट पर एक नज़र डालें और "त्रुटि:" शब्द इनलाइन के साथ सभी मुद्दों को खोजें, उदाहरण के लिए:
15) Removed system variables
Error: Following system variables that were detected as being used will be
removed. Please update your system to not rely on them before the upgrade.
More information: https://dev.mysql.com/doc/refman/8.0/en/added-deprecated-removed.html#optvars-removed
log_builtin_as_identified_by_password - is set and will be removed
show_compatibility_56 - is set and will be removed
एक बार सभी त्रुटियां ठीक हो जाने के बाद, जो भी संभव हो चेतावनियों को कम करने का प्रयास करें। चेतावनियां ज्यादातर MySQL सर्वर की विश्वसनीयता को प्रभावित नहीं करेंगी, लेकिन संभावित रूप से उनके द्वारा उपयोग किए जाने वाले प्रदर्शन या बदले हुए व्यवहार को खराब कर सकती हैं। उदाहरण के लिए, निम्नलिखित चेतावनियों पर एक नज़र डालें:
13) System variables with new default values
Warning: Following system variables that are not defined in your
configuration file will have new default values. Please review if you rely on
their current values and if so define them before performing upgrade.
More information:
https://mysqlserverteam.com/new-defaults-in-mysql-8-0/
back_log - default value will change
character_set_server - default value will change from latin1 to utf8mb4
collation_server - default value will change from latin1_swedish_ci to
utf8mb4_0900_ai_ci
event_scheduler - default value will change from OFF to ON
explicit_defaults_for_timestamp - default value will change from OFF to ON
innodb_autoinc_lock_mode - default value will change from 1 (consecutive) to
2 (interleaved)
innodb_flush_method - default value will change from NULL to fsync (Unix),
unbuffered (Windows)
innodb_flush_neighbors - default value will change from 1 (enable) to 0
(disable)
innodb_max_dirty_pages_pct - default value will change from 75 (%) 90 (%)
innodb_max_dirty_pages_pct_lwm - default value will change from_0 (%) to 10
(%)
innodb_undo_log_truncate - default value will change from OFF to ON
innodb_undo_tablespaces - default value will change from 0 to 2
log_error_verbosity - default value will change from 3 (Notes) to 2 (Warning)
max_allowed_packet - default value will change from 4194304 (4MB) to 67108864
(64MB)
max_error_count - default value will change from 64 to 1024
optimizer_trace_max_mem_size - default value will change from 16KB to 1MB
performance_schema_consumer_events_transactions_current - default value will
change from OFF to ON
performance_schema_consumer_events_transactions_history - default value will
change from OFF to ON
slave_rows_search_algorithms - default value will change from 'INDEX_SCAN,
TABLE_SCAN' to 'INDEX_SCAN, HASH_SCAN'
table_open_cache - default value will change from 2000 to 4000
transaction_write_set_extraction - default value will change from OFF to
XXHASH64
अपग्रेड चेकर उपयोगिता क्या अपेक्षित है इसका एक महत्वपूर्ण अवलोकन प्रदान करती है और अपग्रेड के बाद हमें एक बड़े आश्चर्य से बचाती है।
ClusterControl सलाहकार
ClusterControl में एडवाइजर्स नामक कई आंतरिक मिनी-प्रोग्राम हैं, जहां आप एक छोटा प्रोग्राम लिखते हैं जो ClusterControl ऑब्जेक्ट्स की संरचना के भीतर रहता है और चलता है। आप इसे एक शेड्यूल किए गए फ़ंक्शन के रूप में सोच सकते हैं जो डेवलपर स्टूडियो में बनाई गई स्क्रिप्ट को निष्पादित करता है और एक परिणाम उत्पन्न करता है जिसमें स्थिति, सलाह और औचित्य होता है। यह उपयोगकर्ताओं को कस्टम सलाहकार बनाकर क्लस्टरकंट्रोल की कार्यक्षमता को आसानी से विस्तारित करने की अनुमति देता है जो ऑन-डिमांड या शेड्यूल पर चल सकते हैं।
निम्न स्क्रीनशॉट InnoDB सलाहकारों का एक उदाहरण दिखाता है, जिसे ClusterControl के अंदर सक्रिय और शेड्यूल किए जाने के बाद innodb_log_file_size चेक कहा जाता है:
उपरोक्त परिणाम ClusterControl -> Performance -> सलाहकारों के अंतर्गत देखे जा सकते हैं। प्रत्येक सलाहकार के लिए, यह सलाहकार की स्थिति, डेटाबेस उदाहरण, औचित्य और सलाह को दर्शाता है। शेड्यूल और अंतिम निष्पादन समय के बारे में भी जानकारी है। डेवलपर स्टूडियो के अंतर्गत "संकलित करें और चलाएँ" बटन पर क्लिक करके सलाहकार को ऑन-डिमांड भी निष्पादित किया जा सकता है।
उपरोक्त सलाहकारों में निम्नलिखित कोड होते हैं, जो ClusterControl Domain-Specific Language (DSL) का उपयोग करते हुए लिखे गए हैं, जो काफी हद तक JavaScript के समान है:
#include "common/mysql_helper.js"
#include "cmon/graph.h"
var DESCRIPTION="This advisor calculates the InnoDB log growth per hour and"
" compares it with the innodb_log_file_size configured on the host and"
" notifies you if the InnoDB log growth is higher than what is configured, which is important to avoid IO spikes during flushing.";
var TITLE="Innodb_log_file_size check";
var MINUTES = 20;
function main()
{
var hosts = cluster::mySqlNodes();
var advisorMap = {};
for (idx = 0; idx < hosts.size(); ++idx)
{
host = hosts[idx];
map = host.toMap();
connected = map["connected"];
var advice = new CmonAdvice();
print(" ");
print(host);
print("==========================");
if (!connected)
{
print("Not connected");
continue;
}
if (checkPrecond(host))
{
var configured_logfile_sz = host.sqlSystemVariable("innodb_log_file_size");
var configured_logfile_grps = host.sqlSystemVariable("innodb_log_files_in_group");
if (configured_logfile_sz.isError() || configured_logfile_grps.isError())
{
justification = "";
msg = "Not enough data to calculate";
advice.setTitle(TITLE);
advice.setJustification("");
advice.setAdvice(msg);
advice.setHost(host);
advice.setSeverity(Ok);
advisorMap[idx]= advice;
continue;
}
var endTime = CmonDateTime::currentDateTime();
var startTime = endTime - MINUTES * 60 /*seconds*/;
var stats = host.sqlStats(startTime, endTime);
var array = stats.toArray("created,interval,INNODB_LSN_CURRENT");
if(array[2,0] === #N/A || array[2,0] == "")
{
/* Not all vendors have INNODB_LSN_CURRENT*/
advice.setTitle(TITLE);
advice.setJustification("INNODB_LSN_CURRENT does not exists in"
" this MySQL release.");
advice.setAdvice("Nothing to do.");
advice.setHost(host);
advice.setSeverity(Ok);
advisorMap[idx]= advice;
continue;
}
var firstLSN = array[2,0].toULongLong();
var latestLSN = array[2,array.columns()-1].toULongLong();
var intervalSecs = endTime.toULongLong() - startTime.toULongLong();
var logGrowthPerHourMB = ceiling((latestLSN - firstLSN) * 3600 / 1024/1024 / intervalSecs / configured_logfile_grps);
var logConfiguredMB = configured_logfile_sz/1024/1024;
if (logGrowthPerHourMB > logConfiguredMB)
{
justification = "Innodb is producing " + logGrowthPerHourMB + "MB/hour, and it greater than"
" the configured innodb log file size " + logConfiguredMB + "MB."
" You should set innodb_log_file_size to a value greater than " +
logGrowthPerHourMB + "MB. To change"
" it you must stop the MySQL Server and remove the existing ib_logfileX,"
" and start the server again. Check the MySQL reference manual for max/min values. "
"https://dev.mysql.com/doc/refman/5.6/en/innodb-parameters.html#sysvar_innodb_log_file_size";
msg = "You are recommended to increase the innodb_log_file_size to avoid i/o spikes"
" during flushing.";
advice.setSeverity(Warning);
}
else
{
justification = "Innodb_log_file_size is set to " + logConfiguredMB +
"MB and is greater than the log produced per hour: " +
logGrowthPerHourMB + "MB.";
msg = "Innodb_log_file_size is sized sufficiently.";
advice.setSeverity(Ok);
}
}
else
{
justification = "Server uptime and load is too low.";
msg = "Not enough data to calculate";
advice.setSeverity(0);
}
advice.setHost(host);
advice.setTitle(TITLE);
advice.setJustification(justification);
advice.setAdvice(msg);
advisorMap[idx]= advice;
print(advice.toString("%E"));
}
return advisorMap;
}
ClusterControl सलाहकार को लिखने, संकलित करने, सहेजने, डीबग करने और शेड्यूल करने के लिए डेवलपर स्टूडियो (प्रबंधित -> डेवलपर स्टूडियो के तहत सुलभ) नामक एक आउट-ऑफ-द-बॉक्स एकीकृत विकास वातावरण (IDE) प्रदान करता है:पी>
डेवलपर स्टूडियो और सलाहकारों के साथ, उपयोगकर्ताओं के पास ClusterControl की निगरानी और प्रबंधन कार्यात्मकताओं को विस्तारित करने की कोई सीमा नहीं है। यह सचमुच आपके सभी ओपन-सोर्स डेटाबेस सॉफ़्टवेयर जैसे MySQL, MariaDB, PostgreSQL और MongoDB के साथ-साथ HAProxy, ProxySQL, MaxScale और PgBouncer जैसे लोड बैलेंसर्स के लिए कॉन्फ़िगरेशन जांच को स्वचालित करने के लिए एकदम सही उपकरण है। आप MySQL शेल अपग्रेड चेकर यूटिलिटी का उपयोग करने के लिए एक सलाहकार भी लिख सकते हैं, जैसा कि पिछले अध्याय में दिखाया गया है।
अंतिम विचार
कॉन्फ़िगरेशन जांच और ट्यूनिंग DBA और SysAdmin रूटीन के महत्वपूर्ण भाग हैं ताकि यह सुनिश्चित किया जा सके कि डेटाबेस और रिवर्स प्रॉक्सी जैसे महत्वपूर्ण सिस्टम हमेशा प्रासंगिक और इष्टतम हों क्योंकि आपके वर्कलोड बढ़ते हैं।