Чому InnoDB зберігає всі бази даних в одному файлі?


51

Було зручно, що MyISAM використовував для зберігання кожної таблиці у відповідному файлі. InnoDB досягла вдосконалення в багатьох аспектах, але мені цікаво, чому InnoDB зберігає всі бази даних в одному файлі ( ibdata1за замовчуванням).

Я розумію, що InnoDB буде відображати розташування даних у файлі за окремими файлами індексів для таблиць, але я не розумію, чому він змішує всі дані в одному файлі. І що ще важливіше, навіщо змішувати дані всіх баз даних на сервері?

Цікавою особливістю MyISAM є те, що можна скопіювати / вставити папку бази даних на іншу машину, а потім використовувати базу даних (без дамп).

Відповіді:


66

Архітектура InnoDB вимагає використання чотирьох основних типів інформаційних сторінок

  • Сторінки даних таблиці
  • Сторінки покажчиків таблиць
  • Метадані таблиці
  • Дані MVCC (для підтримки ізоляції транзакцій та відповідності ACID )
    • Відхилення сегментів
    • Скасувати пробіл
    • Подвійний буфер запису (фоновий запис для запобігання надійності на кешування ОС)
    • Вставити буфер (керування змінами не унікальних вторинних індексів)

Дивіться зображальне зображення ibdata1

За замовчуванням innodb_file_per_table вимкнено. Це змушує всі чотири типи інформаційних сторінок вивести один файл під назвою ibdata1. Багато людей намагаються поширити дані, створивши кілька файлів ibdata. Це може призвести до фрагментації даних та індексних сторінок.

Ось чому я часто рекомендую прибирати інфраструктуру InnoDB, використовуючи файл ibdata1 за замовчуванням і більше нічого .

Копіювання дуже небезпечно через інфраструктуру, в якій працює InnoDB. Є дві основні інфраструктури

  • innodb_file_per_table вимкнено
  • innodb_file_per_table увімкнено

InnoDB ( innodb_file_per_table вимкнено)

Якщо вимкнено innodb_file_per_table , всі ці типи інформації InnoDB живуть в ibdata1. Єдиним проявом будь-якої таблиці InnoDB поза ibdata1 є .frm-файл таблиці InnoDB. Копіювання одразу всіх даних InnoDB вимагає копіювання всіх / var / lib / mysql.

Скопіювати окрему таблицю InnoDB абсолютно неможливо. Щоб витягнути дамп таблиці як логічне подання даних та відповідних визначень індексу, ви повинні мати дамп MySQL. Потім ви завантажите цей дамп в іншу базу даних на тому ж сервері чи іншому сервері.

InnoDB ( включений innodb_file_per_table )

Якщо ввімкнено innodb_file_per_table , дані таблиці та її індекси живуть у папці бази даних поруч із файлом .frm. Наприклад, для таблиці db1.mytable, проявом цієї таблиці InnoDB поза ibdata1 буде:

  • /var/lib/mysql/db1/mytable.frm
  • /var/lib/mysql/db1/mytable.ibd

Простір системних таблиць ibdata1

Усі метадані для db1.mytable все ще знаходяться в ibdata1, і цього абсолютно немає . Повторення журналів та даних MVCC також досі живе з ibdata1.

Що стосується фрагментації таблиці, ось що відбувається з ibdata1:

  • innodb_file_per_table увімкнено : ви можете зменшити db1.mytables за допомогоюALTER TABLE db1.mytable ENGINE=InnoDB;абоOPTIMIZE TABLE db1.mytable;. Це призводить до того, що /var/lib/mysql/db1/mytable.ibd є фізично меншим, без фрагментації.
  • innodb_file_per_table вимкнено : ви не можете зменшити db1.mytables зALTER TABLE db1.mytable ENGINE=InnoDB;абоOPTIMIZE TABLE db1.mytable;тому, що він знаходиться з ibdata1. Запустивши будь-яку команду насправді, зробіть таблицю безперервною і швидшою для читання та запису. На жаль, це відбувається наприкінці ibdata1. Це змушує ibdata1 швидко рости. Це повністю вирішено в моєму дописі InnoDB Cleanup .

ПОПЕРЕДЖЕННЯ (або НЕБЕЗПЕЧНО, як би сказав Робот у програші Lost in Space )

Якщо ви думаєте просто скопіювати файли .frm та .ibd, ви стоїте в черзі за все, що завдає шкоди. Копіювання файлів .frm та .ibd таблиці InnoDB добре лише тоді і лише тоді, коли ви можете гарантувати, що ідентифікатор простору таблиць .

Я написав два повідомлення в DBA StackExchange про цю концепцію ідентифікації простору таблиць

Ось відмінна посилання про те , як прикріпити будь-який .ibd файл ibdata1 в разі неузгоджених табличних ідентифікаторів: http://www.chriscalender.com/?tag=innodb-error-tablespace-id-in-file . Прочитавши це, вам слід прийти до негайного усвідомлення того, що копіювання файлів .ibd просто божевільне.

Для InnoDB вам потрібно лише щось перемістити

CREATE TABLE db2.mytable LIKE db1.mytable;
INSERT INTO db2.mytable SELECT * FROM db1.mytable;

зробити копію таблиці InnoDB.

Якщо ви переносите його на інший сервер БД, використовуйте mysqldump.

Що стосується змішування всіх таблиць InnoDB з усіх баз даних, я можу насправді бачити мудрість у цьому. У компанії DB / Web-хостингу мого роботодавця у мене є один клієнт MySQL, який має таблицю в одній базі даних, обмеження яких відображаються в іншій таблиці в іншій базі даних в межах одного екземпляра MySQL. За допомогою одного загального сховища метаданих, це робить можливою підтримку транзакцій та оперативність MVCC в різних базах даних.


Чи означає це, що коли я використовую файл innodb для ввімкненої таблиці і якщо мені потрібно імпортувати свої дані з одного сервера на інший, мені доведеться використовувати тільки mysqldump, а не будь-які інші інструменти, такі як Percona xtrabackup?
tesla747

14

Ви можете переключити InnoDB для зберігання таблиць у файлі, додавши innodb-file-per-table до свого cnf.

Innodb дійсно просто піклується про сторінки даних на базовому рівні. Насправді ви можете налаштувати InnoDB на використання простого блокового пристрою без файлової системи, що ніколи! http://dev.mysql.com/doc/refman/5.5/uk/innodb-raw-devices.html

Існують зручності для зберігання таблиць для файлів, такі як можливість легше відновити використаний простір за допомогою оптимізації.

Навіть з файлами в таблиці ви не можете просто так просто скопіювати файли ibd, оскільки InnoDB є транзакційним і зберігає інформацію про його стан у глобально розповсюджених файлах ibdata / log.

Це не означає, що цього не можна зробити. Якщо таблиця офлайн, ви можете скасувати / імпортувати простори таблиць та скопіювати .idbs навколо http://dev.mysql.com/doc/refman/5.5/uk/innodb-multiple-tablespaces.html


Не сумніваюся, що InnoDB є гнучким двигуном, але я не розумію, наскільки корисне зберігання всіх даних у одному файлі (оскільки ця нова структура була реалізована в InnoDB порівняно з MyISAM).
Googlebot

Я думаю, що це більше одне з цих заднього огляду - це 20/20 речей. Параметр "файл на таблицю" був доданий після того, як innodb вперше скотився з полиць. Зовнішнє надання йому власного блокового пристрою, щоб уникнути накладних витрат файлової системи, я не можу навести причину, чому демпінг їх усіх разом є кращим (і вся справа в блоковому пристрої - це власна дискусія). У всіх моїх настройках innodb увімкнено файл на таблицю.
atxdba

Це суть, не покладаючись на файлову систему, може бути неоціненним, але вона не активна за замовчуванням. Таким чином, декілька користувачів будуть використовувати його.
Googlebot

1
Один варіант файлу на таблицю може завдати шкоди, якщо у вас багато таблиць і мало оперативної пам’яті (наприклад, у магазині Magento може бути близько 1000 таблиць). Налаштування відкритих файлів теж має бути оптимізовано (враховуючи обмеження ОС). Тож використовуйте обережно.
ypercubeᵀᴹ

Це, безумовно, може поставити заслінку на зусилля з відновлення. Так, у вас повинна бути резервна копія, але якщо ви цього не зробите, InnoDB ускладнює справи через цю структуру.
mikato

10

Це поведінка за замовчуванням, але не є обов'язковою. З документів MySQL, використовуючи табличні простори таблиць :

За замовчуванням всі таблиці та індекси InnoDB зберігаються в системному просторі таблиць. Як альтернативу, ви можете зберігати кожну таблицю InnoDB та її індекси у власному файлі . Ця функція називається "декілька табличних просторів", оскільки кожна таблиця, створена під час дії цього параметра, має власну таблицю.

Що стосується того, чому, мабуть, причина полягає в різній архітектурі двох двигунів (MyISAM та InnoDB). Наприклад, в InnoDB ви не можете просто скопіювати .ibd файл в іншу базу даних або установку. Пояснення (з тієї ж сторінки):

Міркування про переносимість файлів .ibd

Ви не можете вільно переміщувати .ibd файли між каталогами баз даних, як це можливо з файлами таблиць MyISAM. Визначення таблиці, що зберігається у спільному просторі таблиць InnoDB, включає ім'я бази даних. Ідентифікатори транзакцій та порядкові номери журналів, що зберігаються у файлах простору таблиць, також відрізняються між базами даних.


Дуже інформативна відповідь і прояснила проблему, але все ж мені цікаво, як великий файл, що містить усі бази даних, може покращити продуктивність (якщо так є).
Googlebot

Продуктивність не краща, оскільки мати один файл для всіх. Різні характеристики, як, наприклад, блокування на рівні рядків, замість рівня таблиці, сприяють продуктивності. Звичайно, головною перевагою є транзакції та обмеження ФК (і, отже, цілісність бази даних).
ypercubeᵀᴹ

1
Ви абсолютно праві щодо сумлінності! Я розумію, чому краще помістити всі таблиці бази даних в один окремий файл; але я не розумію, чому розміщувати всі бази даних (які є абсолютно незалежними) в один і той же файл. InnoDB за замовчуванням використовує лише один файл для зберігання даних.
Googlebot
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.