Content
- 1) Before you start (solid foundation)
- 2) Where to find everything in phpMyAdmin
- 3) Basic maintenance: Check / Analyze / Optimize / Repair
- 4) Indexing and query optimization
- 5) Cleanup & space
- 6) Charset & Collation (recommended: utf8mb4)
- 7) Referential integrity & “orphan” data
- 8) Quick diagnostics from phpMyAdmin
- 9) Real repairs (when something broke)
- 10) Common “recipes” (step by step)
- 11) Quick performance checklist
- 12) Appendix — Useful SQL commands (copy/paste)
- 13) Good to know (common pitfalls)
This article guides you step by step through everything you can do directly in phpMyAdmin to keep your database healthy and fast: checking, analyzing, optimizing, repairing, indexes, charset, collation, plus a few useful SQL recipes. It is written for modern MySQL/MariaDB and assumes you have access to phpMyAdmin with a user that has sufficient privileges.
1) Before you start (solid foundation)
- Mandatory backup. Export the database (SQL) from phpMyAdmin: open the database → Export → “Custom” → include DROP + CREATE.
- Maintenance window. Operations like “Optimize/Analyze” sometimes lock tables. Run them when traffic is low.
- Know your engine.
- InnoDB: default in MySQL 8+. “REPAIR TABLE” does not really apply; “OPTIMIZE” rebuilds the table (equivalent to
ALTER TABLE ... FORCE). - MyISAM: supports
REPAIR TABLE, but consider migrating to InnoDB.
- InnoDB: default in MySQL 8+. “REPAIR TABLE” does not really apply; “OPTIMIZE” rebuilds the table (equivalent to
- Free disk space. Rebuilding tables requires temporary space.
- Permissions. You need
ALTER,INDEX,LOCK TABLESetc. for many operations.
2) Where to find everything in phpMyAdmin
- Select the database in the left column.
- Main tabs: Structure, SQL, Search, Query, Operations, Export/Import.
- At the database level: check multiple tables and use the With selected menu (bottom) → Optimize table, Analyze table, Check table, Repair table.
- At the table level: go to the Operations tab → Table maintenance section (same actions).
- The Structure tab (of a table): manage indexes and columns.
3) Basic maintenance: Check / Analyze / Optimize / Repair
3.1 Check (verification)
- What it does: runs
CHECK TABLEto detect corruption/errors. - How: select tables → With selected → Check table.
- SQL equivalent:
CHECK TABLE `table_name` EXTENDED; - Interpret the result:
status = OKis fine; anything else requires action (Optimize/Repair or server-level intervention).
3.2 Analyze (statistics for the optimizer)
- What it does:
ANALYZE TABLEupdates index statistics; can improve execution plans. - How: With selected → Analyze table.
- SQL:
ANALYZE TABLE `table_name`; - When: after large batches of INSERT/DELETE/UPDATE, or if you see odd EXPLAIN plans.
3.3 Optimize (defragmentation & space)
- What it does:
OPTIMIZE TABLE(InnoDB → rebuilds the table and recreates indexes; reclaims space from “Overhead”). - How: With selected → Optimize table.
- SQL:
OPTIMIZE TABLE `table_name`; - When: when the Overhead column in the table list is high, after many deletes or variable-length column changes (TEXT/VARCHAR).
3.4 Repair (MyISAM only)
- What it does:
REPAIR TABLEtries to fix MyISAM keys/files. - How: With selected → Repair table (active only for MyISAM).
- SQL:
REPAIR TABLE `table_name` QUICK; - Note: for InnoDB, “repair” does not apply. If an InnoDB table seems corrupted, recovery must be done at the server level (backup/restore, recovery options), not in phpMyAdmin.
4) Indexing and query optimization
4.1 Find and create suitable indexes (UI)
- Go to Structure (table) → Indexes section → Create index.
- For composite keys (multi-column), column order matters: put the most selective columns first, used in
WHERE/JOIN/ORDER BY.
4.2 Common SQL operations for indexes
-- Create simple index:
CREATE INDEX idx_users_email ON users(email);
-- Composite index (often searching by (status, created_at)):
CREATE INDEX idx_orders_status_created ON orders(status, created_at);
-- Unique index (ensures uniqueness + speeds up searches):
CREATE UNIQUE INDEX ux_users_email ON users(email);
-- Drop an index (remove unnecessary duplicates):
DROP INDEX idx_old ON users;
-- Show existing indexes:
SHOW INDEX FROM users;
Useful tips:
- Avoid duplicate indexes (e.g. having both
INDEX(email)andUNIQUE(email)— keep onlyUNIQUE). - Index columns used in
WHERE,JOIN,ORDER BY(especially if you sort/filter often). - Prefix index for large columns (e.g.
CREATE INDEX ... ON t(col(100));) if space is an issue. - Don’t over-index. Each index slows down writes. 3–6 indexes/table is usually reasonable (depends on usage).
4.3 EXPLAIN (and EXPLAIN ANALYZE)
In the SQL tab, run:
EXPLAIN SELECT ...;
-- MySQL 8.0.18+ (more detailed):
EXPLAIN ANALYZE SELECT ...;
What you want to see:
typeas selective as possible (ideallyref,range,const, notALL).rowssmall,filteredhigh.Extrashould avoid “Using temporary; Using filesort” on large queries (an appropriate index on sort columns helps).
5) Cleanup & space
- High overhead? Run Optimize on tables with high overhead.
- Migrate to InnoDB: for reliability and row-level locking.
ALTER TABLE table_name ENGINE=InnoDB; - Proper row format (InnoDB):
ALTER TABLE table_name ROW_FORMAT=DYNAMIC;(useful for large TEXT/BLOB columns and modern default compression) - AUTO_INCREMENT gaps are normal; don’t compact just for aesthetics.
6) Charset & Collation (recommended: utf8mb4)
- Why: full Unicode support (emoji, proper diacritics).
- Safe order: server → database → table → column. In phpMyAdmin:
- At the database level: go to Operations → Collation → choose
utf8mb4_0900_ai_ci(MySQL 8) orutf8mb4_general_ci/utf8mb4_unicode_ci(compatible). - At the table level: Operations → Table options → set collation; then convert columns if needed.
- At the database level: go to Operations → Collation → choose
- SQL:
ALTER DATABASE db_name CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci; ALTER TABLE table_name CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci; - Note: make a backup and ensure your application (driver/ORM) uses the same charset/collation.
7) Referential integrity & “orphan” data
- Enable and use foreign keys (InnoDB) for consistency.
- Find “orphan” rows (example):
SELECT c.* FROM comments c LEFT JOIN posts p ON p.id = c.post_id WHERE p.id IS NULL; -- comments without a parent post - Add constraints (after cleanup):
ALTER TABLE comments ADD CONSTRAINT fk_comments_post FOREIGN KEY (post_id) REFERENCES posts(id) ON DELETE CASCADE;
8) Quick diagnostics from phpMyAdmin
- Status / Variables (server level): check load, connections, buffer pool (InnoDB). You can run
SHOW STATUS LIKE 'Threads%';,SHOW ENGINE INNODB STATUS;from the SQL tab for details. - Limitation: persistent configuration changes (e.g.
innodb_buffer_pool_size) belong inmy.cnf— not phpMyAdmin. You can useSET GLOBALfor testing, but it won’t persist after restart.
9) Real repairs (when something broke)
- MyISAM: use
REPAIR TABLEin phpMyAdmin (see §3.4). - InnoDB:
- Try export & re-import via phpMyAdmin if the table is accessible.
- If not, intervention is needed at the server level (restore from backup,
innodb_force_recovery,mysqlcheck). This is not done via phpMyAdmin.
- Server error logs are the source of truth for real corruption cases.
10) Common “recipes” (step by step)
10.1 Quick optimization of the entire database
- Open the desired database.
- Click Check all.
- Menu With selected → Analyze table.
- Then With selected → Optimize table.
- Check the results (all “OK”?).
10.2 Reindexing after a large volume of changes
- Run Check + Analyze (see above).
- Check indexes (tab Structure → Indexes).
- Add/remove indexes based on EXPLAIN.
- Run Optimize if “Overhead” is large.
10.3 Remove unnecessary/duplicate indexes (SQL)
-- Classic duplicate: you have UNIQUE(email) and INDEX(email)
SHOW INDEX FROM users;
-- If you see two entries on the same column, keep the UNIQUE one:
DROP INDEX idx_users_email ON users;
10.4 Mass conversion to utf8mb4 (entire database)
- Full backup.
- Operations (at database level) → set collation to
utf8mb4_0900_ai_ci. - For each table:
ALTER TABLE table_name CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci;
11) Quick performance checklist
- Backup done.
- Check + Analyze run periodically.
- Optimize on tables with high overhead.
- Existing indexes verified (no duplicates, cover WHERE/JOIN/ORDER).
- Slow queries analyzed with EXPLAIN / EXPLAIN ANALYZE.
- Correct charset/collation (utf8mb4).
- Referential integrity active (FK), orphan data cleaned up.
- For serious InnoDB problems: recovery plan at server level (outside phpMyAdmin).
12) Appendix — Useful SQL commands (copy/paste)
-- Table statistics + overhead
SHOW TABLE STATUS FROM db_name LIKE 'table_name';
-- Check / analyze / optimize
CHECK TABLE table_name EXTENDED;
ANALYZE TABLE table_name;
OPTIMIZE TABLE table_name;
-- (MyISAM) Repair
REPAIR TABLE table_name QUICK;
-- Index information
SHOW INDEX FROM table_name;
-- Find tables without primary key
SELECT TABLE_SCHEMA, TABLE_NAME
FROM INFORMATION_SCHEMA.TABLES t
LEFT JOIN (
SELECT TABLE_SCHEMA, TABLE_NAME
FROM INFORMATION_SCHEMA.COLUMNS
WHERE COLUMN_KEY='PRI'
GROUP BY TABLE_SCHEMA, TABLE_NAME
) pk USING (TABLE_SCHEMA, TABLE_NAME)
WHERE pk.TABLE_NAME IS NULL
AND t.TABLE_SCHEMA='db_name';
-- EXPLAIN / EXPLAIN ANALYZE for a query
EXPLAIN SELECT * FROM orders WHERE status='paid' AND created_at >= '2025-01-01';
EXPLAIN ANALYZE SELECT * FROM orders WHERE status='paid' AND created_at >= '2025-01-01';
-- Migration to InnoDB + modern settings
ALTER TABLE table_name ENGINE=InnoDB, ROW_FORMAT=DYNAMIC;
-- Charset/collation conversion
ALTER TABLE table_name CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci;
-- Composite index for filtering + sorting
CREATE INDEX idx_orders_status_created ON orders(status, created_at);
13) Good to know (common pitfalls)
- Locks/performance gaps:
OPTIMIZE/ANALYZEcan lock. Run outside peak hours. - REPAIR is not for InnoDB. If you see the “Repair” button greyed out, it’s normal.
- Don’t rely on old “profiling”. In MySQL 8, use
EXPLAIN ANALYZEinstead ofSET PROFILING=1. SET GLOBALchanges don’t persist. For permanent settings, editmy.cnf(outside phpMyAdmin).- Too many indexes = slow writes. Index with purpose.