মাইএসকিউএল-এ আইবডটা 1 ফাইল সঙ্কুচিত / শুদ্ধ করার উপায়


561

আমি আর-তে পরিসংখ্যান সম্পাদনের জন্য লোকালহোস্টে মাইএসকিউএলকে একটি "ক্যোয়ারী সরঞ্জাম" হিসাবে ব্যবহার করছি, অর্থাৎ প্রতিবার আমি আর স্ক্রিপ্ট চালাচ্ছি, আমি একটি নতুন ডাটাবেস (এ) তৈরি করি, একটি নতুন টেবিল (বি) তৈরি করি, বিতে ডেটা আমদানি করি আমার যা প্রয়োজন তা পেতে একটি ক্যোয়ারী জমা দিন এবং তারপরে আমি বি ড্রপ করব এবং এ।

এটি আমার পক্ষে ঠিকঠাক কাজ করছে, তবে আমি বুঝতে পারি যে ইবদাটা ফাইলের আকার দ্রুত বাড়ছে, আমি মাইএসকিউএল-তে কিছুই সঞ্চয় করি নি, তবে ইবদাতা 1 ফাইলটি ইতিমধ্যে 100 এমবি ছাড়িয়েছে।

আমি সেটআপের জন্য কম-বেশি ডিফল্ট মাইএসকিউএল সেটিংস ব্যবহার করছি, একটি নির্দিষ্ট সময়ের পরে আমি ইবদাতা 1 ফাইলটি স্বয়ংক্রিয়ভাবে সঙ্কুচিত / শুদ্ধ করতে পারি এমন কোনও উপায় আছে কি?


আরও রেফারেন্স: ইনেডাটা
hakre

উত্তর:


777

এটি ibdata1সঙ্কুচিত হয় না মাইএসকিউএলের একটি বিশেষ বিরক্তিকর বৈশিষ্ট্য। ibdata1ফাইল আসলে, যদি না আপনি সব ডাটাবেস মুছে দিন, ফাইল মুছে ফেলুন এবং একটি ডাম্প পুনরায় লোড সঙ্কুচিত করা যাবে না।

তবে আপনি মাইএসকিউএল কনফিগার করতে পারেন যাতে প্রতিটি সারণী, এর সূচীগুলি সহ একটি পৃথক ফাইল হিসাবে সংরক্ষণ করা হয়। এভাবে ibdata1বড় হিসাবে হত্তয়া করা হবে না। মতে বিল Karwin এর মন্তব্য এই মাইএসকিউএল সংস্করণ 5.6.6 হিসাবে ডিফল্টরূপে সক্রিয় করা হয়।

কিছুক্ষণ আগে আমি এটি করেছি। তবে, প্রতিটি টেবিলের জন্য পৃথক ফাইলগুলি ব্যবহার করার জন্য আপনার সার্ভারটি সেটআপ করতে my.cnfআপনাকে এটি সক্ষম করার জন্য পরিবর্তন করতে হবে:

[mysqld]
innodb_file_per_table=1

http://dev.mysql.com/doc/refman/5.5/en/innodb-multiple-tablespaces.html

আপনার কাছ থেকে স্থানটি দাবি করতে চাইলে ibdata1আসলে ফাইলটি মুছতে হবে:

  1. কি একটি mysqldumpসব ডেটাবেস পদ্ধতি ট্রিগার ইত্যাদি ব্যতীত mysqlএবং performance_schemaডাটাবেস
  2. উপরের ২ টি ডাটাবেস বাদে সমস্ত ডাটাবেস ফেলে দিন
  3. বন্ধ করুন mysql
  4. মুছুন ibdata1এবং ib_logফাইল
  5. মাইএসকিএল শুরু করুন
  6. ডাম্প থেকে পুনরুদ্ধার করুন

আপনি যখন মাইএসকিউএল শুরু করবেন 5 ধাপে ibdata1এবং ib_logফাইলগুলি পুনরায় তৈরি করা হবে।

এখন আপনি যেতে ফিট। আপনি যখন বিশ্লেষণের জন্য একটি নতুন ডাটাবেস তৈরি করেন, সারণীগুলি পৃথক ibd*ফাইলে অবস্থিত হবে না ibdata1। আপনি অল্প সময়ের মধ্যেই ডাটাবেসটি ফেলে রাখার সাথে সাথে ibd*ফাইলগুলি মুছে ফেলা হবে।

http://dev.mysql.com/doc/refman/5.1/en/drop-database.html

আপনি সম্ভবত এটি দেখেছেন:
http://bugs.mysql.com/bug.php?id=1341

কমান্ডটি ব্যবহার করে ALTER TABLE <tablename> ENGINE=innodbবা OPTIMIZE TABLE <tablename>কেউ আইবডেটা 1 থেকে আলাদা ফাইলগুলিতে ডেটা এবং সূচী পৃষ্ঠাগুলি বের করতে পারে। তবে উপরের পদক্ষেপগুলি না করা থাকলে ইবদাটা 1 সঙ্কুচিত হবে না।

সম্পর্কিত information_schema, যে ড্রপ করা প্রয়োজন হয় না বা সম্ভব। এটি আসলে সারণী নয়, কেবল পঠনযোগ্য দেখার একগুচ্ছ। এবং তাদের সাথে কোনও ফাইল যুক্ত নেই, এমনকি কোনও ডাটাবেস ডিরেক্টরিও নেই। informations_schemaমেমরি ডিবি-ইঞ্জিন ব্যবহার করা হয় এবং বাদ পড়েছে এবং স্টপ উপর দ্বিজ হয় / mysqld এর পুনরায় আরম্ভ করুন। Https://dev.mysql.com/doc/refman/5.7/en/information-schema.html দেখুন ।


16
@ জর্ডান ম্যাগনুসন তথ্য_স্কেমা ফেলে দেওয়ার বিরক্ত করবেন না। এটি আসলে সারণী নয়, কেবল পঠনযোগ্য দেখার একগুচ্ছ। এবং তাদের সাথে কোনও ফাইল যুক্ত নেই। এমনকি ডাটাবেসের জন্য একটি ডিরেক্টরি নেই। তথ্য_সেমিমা মেমরি ডিবি-ইঞ্জিন ব্যবহার করছে এবং ফেলে দেওয়া এবং মাইএসকিএলএল স্টপ / পুনরায় চালু করার পরে পুনরায় জেনারেট করা হয়। Dev.mysql.com/doc/refman/5.5/en/information-schema.html দেখুন । পারফরম্যান্স_স্কেমা সম্পর্কে আমি নিজেও সেই স্কিমা ব্যবহার করি নি।
জন পি

4
আমি জানি না এটি সাম্প্রতিক জিনিস কিনা তবে একবার ইনোডাব_ফিল_পিটার_সারণযোগ্য বিকল্পটি সক্ষম হয়ে গেলে আপনি কেবল "ALTER TABLE <tablename> ENGINE = InnoDB" চালাতে পারবেন (যদিও এটি ইতিমধ্যে InnoDB) এবং এটি টেবিলটিকে তার পৃথক ফাইলে সরিয়ে ফেলবে । ডেটাবেস এবং এই ধরনের ড্রপ করার প্রয়োজন নেই।
সিআর

3
+1 FWIW, মাইএসকিউএল 5.6 innodb_file_per_tableডিফল্টরূপে সক্ষম করে।
বিল কারভিন

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

1
আমার সার্ভারে আইবডটা 1 ফাইলের কারণে আমি খুব কম স্থান পেয়েছি, তাই আমি ডাটাবেসগুলিও ফেলে দিতে পারি না। / Var / lib / mysql ("mysql", "ibdata1", "ib_logfile0" এবং "ib_logfile1" বাদে) ফাইলগুলি সরানো এবং তারপরে পদক্ষেপগুলি অনুসরণ করা কি একই রকম হবে? দেখুন stackoverflow.com/questions/2482491/...
Sophivorus

47

জন পি এর উত্তর যোগ করা ,

একটি লিনাক্স সিস্টেমের জন্য, 1-6 পদক্ষেপগুলি এই কমান্ডগুলির সাহায্যে সম্পন্ন করা যেতে পারে:

  1. mysqldump -u [username] -p[root_password] [database_name] > dumpfilename.sql
  2. DROP DATABASE [database_name];
  3. sudo /etc/init.d/mysqld stop
  4. sudo rm /var/lib/mysql/ibdata1
    sudo rm /var/lib/mysql/ib_logfile (এবং অন্য কোন ib_logfile এর যে নাম দেওয়া যেতে পারে মুছতে ib_logfile0, ib_logfile1ইত্যাদি ...)
  5. sudo /etc/init.d/mysqld start
  6. create database [database_name];
  7. mysql -u [username]-p[root_password] [database_name] < dumpfilename.sql

সতর্কতা: এই নির্দেশাবলী আপনাকে অন্য ডেটাবেসগুলি হারাতে বাধ্য করবে যদি আপনার এই মাইএসকিএল উদাহরণে অন্য ডাটাবেস থাকে। আপনি যে ডেটাবেস রাখতে চান তাতে 1,2 এবং 6,7 পদক্ষেপগুলি সংশোধিত হয়েছে তা নিশ্চিত করুন।


6
InnoDB টেবিল রয়েছে এমন প্রতিটি ডাটাবেসের জন্য আপনাকে 1,2 এবং 6 টি পুনরাবৃত্তি করতে হবে।
মারকুইস

4
আপনার # 5 এবং # 6 এর মধ্যে আরও কয়েকটি ধাপ প্রয়োজন। আপনাকে ডাটাবেসটি পুনরায় তৈরি করতে হবে এবং অনুমতিগুলি পুনরায় বরাদ্দ করতে হবে। সুতরাং mysql ক্লায়েন্ট কমান্ড প্রম্পট থেকে create database database_name;এবং তারপরেgrant all privileges on database_name.* to 'username'@'localhost' identified by 'password';
ফ্রেড

1
@ ফ্রেড এটি করার সময় আমার কোনও সুযোগ সুবিধা দেওয়ার দরকার পড়েনি। সম্ভবত আমি একই নামের সাথে ডাটাবেসটি পুনরায় তৈরি করেছি বলে?
crmpicco

2
কোনও Password:প্রম্পটে পাসওয়ার্ড টাইপ করতে (যা একটি নিরাপদ অনুশীলন), কেবল -pকোনও আসল পাসওয়ার্ড ছাড়াই রাখুন।
ADTC

ট্রিগার, ইভেন্ট এবং রুটিন / ফাংশন ডাম্প করা হয় না যতক্ষণ না আপনি মাইএসকিल्डম্পকে এটি করতে বলে। --Trigger, --events এবং --routines পাশাপাশি যুক্ত করুন যদি আপনার কোনও ডাটাবেসে থাকে। এছাড়াও, সমস্ত ডাটাবেস একে একে একের পরিবর্তে একবারে ডাম্প করার জন্য - সমস্ত-ডাটাবেসগুলি দিয়ে ডাম্প করুন।
ফ্রিয়েক

34

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

কীভাবে বিদ্যমান ইবদাটা ফাইল সঙ্কুচিত করবেন:

http://dev.mysql.com/doc/refman/5.5/en/innodb-resize-system-tablespace.html

আপনি এটিকে স্ক্রিপ্ট করতে পারেন এবং একটি নির্দিষ্ট সময়ের পরে স্ক্রিপ্টটি চালানোর জন্য নির্ধারণ করতে পারেন, তবে উপরে বর্ণিত সেটআপের জন্য মনে হয় একাধিক টেবিল স্পেসগুলি একটি সহজ সমাধান।

আপনি যদি কনফিগারেশন বিকল্পটি ব্যবহার করেন তবে আপনি innodb_file_per_tableএকাধিক টেবিল স্পেস তৈরি করেন। অর্থাৎ, মাইএসকিউএল একটি ভাগ করা ফাইলের পরিবর্তে প্রতিটি টেবিলের জন্য পৃথক ফাইল তৈরি করে। এই পৃথক ফাইলগুলি ডাটাবেসের ডিরেক্টরিতে সঞ্চিত থাকে এবং আপনি যখন এই ডাটাবেসটি মুছবেন তখন সেগুলি মুছে ফেলা হবে। এটি আপনার ক্ষেত্রে ইবদাতা ফাইলগুলি সঙ্কুচিত / শুদ্ধ করার প্রয়োজনীয়তা সরিয়ে ফেলবে।

একাধিক টেবিল স্পেস সম্পর্কে আরও তথ্য:

http://dev.mysql.com/doc/refman/5.5/en/innodb-multiple-tablespaces.html


প্রথম লিঙ্কটি ভাঙা, নিকটতম ম্যাচটি আমি খুঁজে পেতে পারি: dev.mysql.com/doc/refman/5.5/en/…
ব্ল্যাকইস

14

আপনি যদি আপনার মাইএসকিউএল টেবিলগুলির জন্য (কিছু) জন্য InnoDB স্টোরেজ ইঞ্জিন ব্যবহার করেন তবে আপনি সম্ভবত ইতিমধ্যে এর ডিফল্ট কনফিগারেশন নিয়ে কোনও সমস্যা পেয়ে এসেছেন। আপনি যেমনটি আপনার মাইএসকিউএল এর ডেটা ডিরেক্টরিতে লক্ষ্য করেছেন (ডেবিয়ান / উবুন্টু - / var / lib / mysql তে) 'আইবডাটা 1' নামে একটি ফাইল রয়েছে ′ এটি মাইএসকিউএল ইনস্ট্যান্সের প্রায় সমস্ত ইনোডিবি ডেটা (এটি কোনও লেনদেনের লগ নয়) ধারণ করে এবং এটি বেশ বড় আকার ধারণ করতে পারে। ডিফল্টরূপে এই ফাইলটির প্রাথমিক আকার 10Mb থাকে এবং এটি স্বয়ংক্রিয়ভাবে প্রসারিত হয়। দুর্ভাগ্যক্রমে, ডিজাইনের মাধ্যমে InnoDB ডেটা ফাইল সঙ্কুচিত করা যায় না। এজন্যই ডিলেট, ট্রানসেটস, ড্রপস ইত্যাদি ফাইল দ্বারা ব্যবহৃত স্থানটিকে পুনরায় দাবি করতে পারবে না।

আমি মনে করি আপনি সেখানে ভাল ব্যাখ্যা এবং সমাধান খুঁজে পেতে পারেন:

http://vdachev.net/2007/02/22/mysql-reducing-ibdata1/


11

ব্যাশটিতে গৃহীত উত্তরের প্রক্রিয়াটি দ্রুত স্ক্রিপ্ট করুন:

#!/usr/bin/env bash
DATABASES="$(mysql -e 'show databases \G' | grep "^Database" | grep -v '^Database: mysql$\|^Database: binlog$\|^Database: performance_schema\|^Database: information_schema' | sed 's/^Database: //g')"
mysqldump --databases $DATABASES -r alldatabases.sql && echo "$DATABASES" | while read -r DB; do
    mysql -e "drop database \`$DB\`"
done && \
    /etc/init.d/mysql stop && \
    find /var/lib/mysql -maxdepth 1 -type f \( -name 'ibdata1' -or -name 'ib_logfile*' \) -delete && \
    /etc/init.d/mysql start && \
    mysql < alldatabases.sql && \
    rm -f alldatabases.sql

হিসাবে সংরক্ষণ করুন purge_binlogs.shএবং হিসাবে চালান root

তথ্য বাদ দেওয়া mysql, information_schema, performance_schema(এবং binlogডিরেক্টরির)।

ধরে নিন আপনার প্রশাসকের শংসাপত্র রয়েছে /root/.my.cnfএবং আপনার ডাটাবেসটি ডিফল্ট /var/lib/mysqlডিরেক্টরিতে থাকে।

এর সাথে আরও ডিস্কের স্থান ফিরে পেতে আপনি এই স্ক্রিপ্টটি চালানোর পরে বাইনারি লগগুলিও পরিষ্কার করতে পারেন:

PURGE BINARY LOGS BEFORE CURRENT_TIMESTAMP;

এখনও নিশ্চিত না কেন তবে আজ আমার কিছু ইনোডিবি টেবিল একই ধরণের প্রক্রিয়া চলাকালীন কলুষিত হয়েছিল, তাই alldatabases.sqlডাবল চেক করার আগে আমি সমস্ত সারণী স্বাস্থ্যকর কিনা তা সরিয়ে ফেলব না । কিছু উন্নতি হিসাবে: innodb_fast_shutdown=0শাটডাউন করার autocommit=0আগে সেট করুন, এসকিউএল ফাইল আমদানির আগে সেট করুন, এসকিউএল ফাইল আমদানির পরে নির্বাহ করুন COMMITএবং সেট autocommit=1করুন, mysqlcheck --all-databasesব্যাকআপ মোছার আগে ব্যবহার করুন ।
ভিক্টর

6

যদি আপনার লক্ষ্য মাইএসকিউএল মুক্ত স্থান নিরীক্ষণ করা হয় এবং আপনি মাইএসকিউএলকে আপনার ইবদাটা ফাইল সঙ্কুচিত করতে থামাতে না পারেন, তবে তা টেবিলের স্থিতি কমান্ডের মাধ্যমে পান। উদাহরণ:

মাইএসকিউএল> 5.1.24:

mysqlshow --status myInnodbDatabase myTable | awk '{print $20}'

মাইএসকিউএল <5.1.24:

mysqlshow --status myInnodbDatabase myTable | awk '{print $35}'

তারপরে এই মানটিকে আপনার ইবদাটা ফাইলের সাথে তুলনা করুন:

du -b ibdata1

সূত্র: http://dev.mysql.com/doc/refman/5.1/en/show-table-status.html


4

উপরের মাইএসকিএল-সার্ভারের রেসিপিগুলির একটি নতুন সংস্করণে "মাইএসকিএল" ডাটাবেস ক্রাশ করবে। পুরানো সংস্করণে এটি কাজ করে। নতুন কিছু টেবিলগুলি INNODB টেবিল প্রকারে স্যুইচ করে এবং এটি করে আপনি তাদের ক্ষতি করতে পারেন। সবচেয়ে সহজ উপায়:

  • আপনার সমস্ত ডাটাবেস ডাম্প
  • মাইএসকিএল-সার্ভারটি আনইনস্টল করুন,
  • মাই সিএনএফ এ যুক্ত করুন:
    [mysqld]
    innodb_file_per_table=1
  • / var / lib / mysql এ সমস্ত মুছুন
  • মাইএসকিএল-সার্ভার ইনস্টল করুন
  • ব্যবহারকারী এবং ডাটাবেস পুনরুদ্ধার

1

ইতিমধ্যে উল্লিখিত হিসাবে আপনি ইবদাতা 1 সঙ্কুচিত করতে পারবেন না (এটি করার জন্য আপনাকে ডাম্প এবং পুনর্নির্মাণের প্রয়োজন), তবে এর আসল প্রয়োজনও প্রায়শই নেই।

অটোএকসেট (সম্ভবত সর্বাধিক সাধারণ আকারের সেটিং) ব্যবহার করে আইবডাটা 1 স্টোরেজটি পূর্বনির্ধারণ করে, প্রতিবার এটি প্রায় পূর্ণ হয়ে ওঠে growing স্থানটি ইতিমধ্যে বরাদ্দ হওয়ায় এটি দ্রুত লেখায়।

আপনি যখন ডেটা মুছবেন তখন এটি সঙ্কুচিত হয় না তবে ফাইলের অভ্যন্তরের স্থানটি অব্যবহৃত হিসাবে চিহ্নিত করা হয়। এখন আপনি নতুন ডেটা inোকানোর পরে ফাইলটি আরও বাড়ানোর আগে এটি খালি স্থানটি পুনরায় ব্যবহার করবে।

সুতরাং কেবলমাত্র যদি আপনার সেই ডেটার প্রয়োজন হয় তবে এটি বাড়তে থাকবে। অন্য অ্যাপ্লিকেশনের জন্য যদি আপনার সত্যিকারের জায়গার প্রয়োজন না হয় তবে এটি সঙ্কুচিত হওয়ার সম্ভবত কোনও কারণ নেই।


66
আমি মনে করি আপনি স্থানটি খালি করার প্রয়োজনের থেকে কিছুটা বঞ্চিত হন।

2
আমার একটি 60 জিগ সলিড স্টেট পার্টিশন রয়েছে। আমি 4 + জিগ ডাটাবেস নিয়ে কাজ করার পরে, আমি খুব দ্রুত স্পেসের বাইরে চলে এসেছি। আমি শিগগিরই অন্য এক বিভাজনে
মাইএসকিএল

3
এই উত্তরের জন্য আপনাকে ধন্যবাদ, এটি খুব সহায়ক। আমি লিগ্যাসির ডেটা থেকে কিছু সারণী সাফ করে দিয়েছি ... এটা জেনে রাখা ভাল যে ডিস্কের আকার শীঘ্রই আর আর বাড়বে না।
ব্র্যাড

1
আমার কাছে 500 জি ইবদাটা 1 ফাইল রয়েছে - তবে এতে যে ডেটা সংরক্ষণ করা হয়েছিল তার প্রায় সবই এখন প্রতি ডাটাবেস ফাইলগুলিতে সঞ্চিত। আমার এই স্থানের অবিচ্ছিন্ন বর্জ্য সঙ্কুচিত করার খুব দরকার!
ফ্র্যাঙ্কস্টার

2
সম্পূর্ণ বাজে! একটি ফাইল যে bloating রাখে ছাঁটা করা প্রয়োজন কিনা আপনি স্থান ফুরিয়ে আসছে বা না । আমি এটি একটি কল করবে storage leak
ADTC
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.