সক্রিয় পড়া এবং লেখার সাথে লাইভ সিস্টেমে মাইএসকিএলডাম সঞ্চালনের নিরাপদতম উপায়?


78

আমি এটি সত্য কিনা তা নিশ্চিত নই তবে আপনি নীচের কমান্ডটি লিনাক্সটিতে চালাচ্ছেন কিনা তা মনে পড়ে

mysqldump -u username -p database_name > backup_db.sql

যখন পাঠ্য এবং লেখাগুলি একটি ডাটাবেসে তৈরি করা হচ্ছে তখন ডাম্পটিতে ত্রুটি থাকতে পারে।

mysqldumpলাইভ সিস্টেমে নিরাপদে এটি সম্পন্ন হয়েছে তা নিশ্চিত করার জন্য কমান্ডের কোনও বিশেষ বিকল্প রয়েছে ? আমাদের ব্যবহারকারীদের জন্য কয়েক সেকেন্ডের জন্য পাঠ্য / লেখার অক্ষম থাকা নিয়ে আমি ঠিক আছি (ডাটাবেস <50MB)

উত্তর:


82

সমস্ত ডেটা ইনোডিবি

এটি আপনাকে ডেটার একটি সঠিক পয়েন্ট ইন টাইম স্ন্যাপশট দেবে:

mysqldump -uuser -ppass --single-transaction --routines --triggers --all-databases > backup_db.sql

--single-transactionএকটি চেকপয়েন্ট তৈরি করে যা আগত পরিবর্তনগুলি গ্রহণ করার সময় ডাম্পটিকে চেকপয়েন্টের আগে সমস্ত ডেটা ক্যাপচার করতে দেয়। আগত পরিবর্তনগুলি ডাম্পের অংশ হয় না। এটি সমস্ত টেবিলের জন্য একই পয়েন্ট ইন সময় নিশ্চিত করে।

--routines সমস্ত সঞ্চিত পদ্ধতি এবং সঞ্চিত কার্যাদি ডাম্প করে

--triggers প্রতিটি টেবিলের জন্য সমস্ত ট্রিগার ডাম্প করে

সমস্ত ডেটা মাইআইএসএএম বা মিক্স অফ ইনোডিবি / মাইআইএসএএম

আপনাকে একটি গ্লোবাল রিড লক চাপিয়ে দিতে হবে, মাইএসকিএলডাম করতে হবে এবং গ্লোবাল লকটি প্রকাশ করতে হবে

mysql -uuser -ppass -Ae"FLUSH TABLES WITH READ LOCK; SELECT SLEEP(86400)" &
sleep 5
mysql -uuser -ppass -ANe"SHOW PROCESSLIST" | grep "SELECT SLEEP(86400)" > /tmp/proclist.txt
SLEEP_ID=`cat /tmp/proclist.txt | awk '{print $1}'`
echo "KILL ${SLEEP_ID};" > /tmp/kill_sleep.sql
mysqldump -uuser -ppass --single-transaction --routines --triggers --all-databases > backup_db.sql
mysql -uuser -ppass -A < /tmp/kill_sleep.sql

একবার চেষ্টা করে দেখো !!!

আপডেট 2012-06-22 08:12 ইডিটি

যেহেতু আপনার কাছে মোট ডেটা <50MB রয়েছে আমার কাছে অন্য একটি বিকল্প রয়েছে। 86400 সেকেন্ডের জন্য গ্লোবাল রিড লকটি ধরে রাখার জন্য ব্যাকগ্রাউন্ডে একটি স্লাইপ কমান্ড প্রবর্তনের পরিবর্তে (24 ঘন্টা) কেবল প্রক্রিয়া আইডি পেতে এবং বাইরে হত্যা করার জন্য, আসুন ওএসের পরিবর্তে মাইএসকিএলে একটি 5 সেকেন্ড টাইমআউট সেট করার চেষ্টা করুন:

SLEEP_TIMEOUT=5
SQLSTMT="FLUSH TABLES WITH READ LOCK; SELECT SLEEP(${SLEEP_TIMEOUT})"
mysql -uuser -ppass -Ae"${SQLSTMT}" &
mysqldump -uuser -ppass --single-transaction --routines --triggers --all-databases > backup_db.sql

এটি খুব ছোট ডাটাবেসের জন্য একটি ক্লিনার এবং সহজ পদ্ধতির।


1
5 সেকেন্ড কেবল সতর্কতামূলক। আপনি নিম্ন মানের চেষ্টা করতে পারেন।
RolandoMySQLDBA

1
রোল্যান্ডো - ERROR 2013 (HY000) at line 1: Lost connection to MySQL server during queryএকটি প্রত্যাশিত ত্রুটি বার্তা?
ব্যবহারকারী 784637

1
সমস্ত মাইএসকিউএল ডেটা কি মাইএসকিএলডাম্পে এসেছিল?
রোল্যান্ডোমাইএসকিউএলডিবিএ

1
আমি ত্রুটি বার্তা সম্পর্কে নিশ্চিত নই। এটি কেবলমাত্র অনুমান, তবে এটি সম্ভবত দ্বিতীয় স্ক্রিপ্টে উল্লিখিত ব্যবহারকারী-সংজ্ঞায়িত SLEEP ফাংশন কলটিকে হত্যা করে এমন এক-লাইন স্ক্রিপ্ট থেকে এসেছে।
রোল্যান্ডোমাইএসকিউএলডিবিএ

1
আমার নতুন পরামর্শটি চেষ্টা করে দেখুন এটি ভাল হয় কিনা। আশা করি, কোনও ত্রুটির বার্তা থাকবে না।
রোল্যান্ডোমাইএসকিউএলডিবিএ


1

আপনি যদি টেবিলগুলি লক না করে মাইআইএসএএম বা মিশ্র টেবিলগুলির কোনও ডাউনটাইম ছাড়াই এটি করতে চান তবে আপনি একটি স্লেভ ডাটাবেস সেট আপ করতে পারেন এবং সেখান থেকে আপনার স্ন্যাপশটগুলি নিতে পারেন। দুর্ভাগ্যক্রমে স্লেভ ডাটাবেস সেটআপ করার ফলে কিছুটা ডাউনটাইম লাইভ ডাটাবেস রফতানি হয়, তবে এটি একবার চলার পরে, আপনি এটির টেবিলগুলি লক করতে সক্ষম হবেন এবং অন্যরা বর্ণিত পদ্ধতিগুলি ব্যবহার করে রফতানি করতে পারবেন। এটি যখন ঘটবে, তখন এটি মাস্টারের পিছনে থাকবে, তবে মাস্টারটিকে তার টেবিলগুলি আপডেট করা থেকে বিরত করবে না এবং ব্যাকআপটি শেষ হওয়ার সাথে সাথেই তা ধরা পড়বে।


1

আমি এটি কীভাবে করেছি তা এখানে। এটি যেহেতু এটি ব্যবহার করে সব ক্ষেত্রে এটি কাজ করা উচিত FLUSH TABLES WITH READ LOCK

#!/bin/bash

DB=example
DUMP_FILE=export.sql

# Lock the database and sleep in background task
mysql -uroot -proot $DB -e "FLUSH TABLES WITH READ LOCK; DO SLEEP(3600);" &
sleep 3

# Export the database while it is locked
mysqldump -uroot -proot --opt $DB > $DUMP_FILE

# When finished, kill the previous background task to unlock
kill $! 2>/dev/null
wait $! 2>/dev/null

echo "Finished export, and unlocked !"

শেল sleepকমান্ডটি কেবল তা নিশ্চিত করার জন্য যে মাইএসকিএলডাম্প কমান্ড চলমান ব্যাকগ্রাউন্ড টাস্কটি মাইএসকিএলডাম্প শুরু হওয়ার আগেই সম্পাদিত হয়েছিল। আপনি এটি 1 সেকেন্ডে কমাতে পারেন এবং এটি এখনও ঠিক থাকতে হবে। এটি 30 সেকেন্ডে বাড়িয়ে নিন এবং 30 ক্লাবের মধ্যে অন্য ক্লায়েন্টের কাছ থেকে কোনও টেবিলে কোনও মান সন্নিবেশ করানোর চেষ্টা করুন আপনি দেখতে পাবেন এটি লক হয়েছে।

mysqldumpবিকল্পগুলি ব্যবহার করার পরিবর্তে এই ম্যানুয়াল পটভূমির লকটি ব্যবহার করার 2 টি সুবিধা রয়েছে --single-transactionএবং --lock-tables:

  1. আপনি মাইআইএসএএম / ইনোডিবি টেবিলগুলি মিশ্রিত করলে এটি সমস্ত কিছু লক করে দেয়।
  2. আপনি mysqldumpএকই লকিং সময়কালে ছাড়াও অন্যান্য কমান্ড চালাতে পারেন । উদাহরণস্বরূপ, মাস্টার নোডে প্রতিলিপি স্থাপন করার সময় এটি দরকারী, কারণ SHOW MASTER STATUS;প্রতিলিপি স্লেভ তৈরি করতে সক্ষম হবার জন্য আপনার তৈরি ডাম্পের সঠিক অবস্থানে (ডাটাবেস আনলক করার আগে) বাইনারি লগ অবস্থান আপনার প্রয়োজন ।

1

মাইএসকিএল অফিসিয়াল ডকুমেন্টেশনের পরামর্শটি হ'ল আপনার একটি মাস্টার "এম 1" ডাটাবেস এবং একটি স্লেভ "এস 1" ডাটাবেস থাকা উচিত যা "পরিস্থিতি 2: একটি পঠন-পঠন স্লেভের সাথে ব্যাকআপ" এর মাধ্যমে একটি মাস্টার বা দাসকে ব্যাকআপ আপ করার মাধ্যমে বর্ণনা করা হয়েছে শুধুমাত্র পাঠযোগ্য

আপনার স্লেভ ডাটাবেসটি কেবল পঠন এবং সেট করা উচিত


0

আপনার যদি খুব বড় মাইআইএসএএম টেবিল থাকে এবং আপনার লক ছাড়াই টেবিলটি ডাম্প করা এবং উচ্চ সার্ভারের লোড এড়ানো দরকার হয়, আপনি নিম্নলিখিত স্ক্রিপ্টটি ব্যবহার করতে পারেন।

#!/bin/sh

my_user="user"
my_password="password"
my_db="vpn"
my_table="traffic"
my_step=100000

read -p "Dumping table ${my_db}.${my_table} to ${my_table}.sql?" yn
case $yn in
    [Yy]* ) break;;
    * ) echo "User cancel."; exit;;
esac

my_count=$(mysql $my_db -u $my_user -p$my_password -se "SELECT count(*) FROM $my_table")
my_count=$(($my_count + 0))

if [ ! $my_count ]
then
    echo "No records found"
    exit
fi

echo "Records in table ${my_db}.${my_table}: ${my_count}"

echo "" > $my_table.sql

max_progress=60

for (( limit=0; limit<=$my_count; limit+=$my_step )); do
    progress=$((max_progress * ( limit + my_step) / my_count))

    echo -ne "Dumping ["
    for ((i=0; i<$progress; i ++)); do
        echo -ne "#"
    done
    for ((; i<$max_progress; i ++)); do
        echo -ne "."
    done

    mysqldump -u $my_user -p$my_password --complete-insert --no-create-info --opt --where="1 limit $limit , $my_step" $my_db $my_table >> $my_table.sql
    echo "" >> $my_table.sql

    echo -ne "] $((100 * ( limit + my_step ) / my_count)) %"
    echo -ne "\r"

    sleep 1

done

echo -ne "\n"
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.