Write a script that will create a script
MYSQL_CONN="-hAmazonRDSDNSName -u... -p..."
SQL="SELECT CONCAT('OPTIMIZE TABLE ',table_schema,'.',table_name,';')"
SQL="${SQL} OptimizeTableSQL FROM information_schema.tables WHERE table_schema = 'signs'"
SQL="${SQL} ORDER BY (data_length+index_length)"
mysql ${MYSQL_CONN} -AN -e"${SQL}" > /root/OptimizeAllTables.sql
less /root/OptimizeAllTables.sql
When you are satisfied that the script will do the job then do this:
mysql ${MYSQL_CONN} < /root/OptimizeAllTables.sql
Give it a Try !!!
CAVEAT
Since the default for innodb_file_per_table is ON, each InnoDB table being optimized will actually have its .ibd
file shrunk. Any MyISAM tables (which I hope you don't have) will also have their .MYD
and .MYI
files shrunk as well.
UPDATE 2012-09-18 18:19 EDT
I just tried the following:
- Created Instance1 with 5G Disk
- Modified Instance1 to 10G Disk
- Modified Instance1 to 5G Disk (error message :
Requested storage size (5) cannot be less then the current storage size (10)
)
- Create Instance2 with 5G
- Loaded Instance1 with 2MB data
- Created Snapshot of Instance1 (same size : 10G)
If I restore the snapshot, it creates a third Instance. DB Snapshot must be the whole Server Instance, not a dump of any kind.
You will have to do the following messy procedure:
- mysqldump the data from the 20GB Instance
- Create a New 10G Instance
- load the mysqldump into the new 10GB instance
- verify all the data you want is present
- destroy the old 20GB
At step 4, please run this Big Storage Engine Space Query on both the 20GB and 10GB instances
SELECT IFNULL(B.engine,'Total') "Storage Engine",
CONCAT(LPAD(REPLACE(FORMAT(B.DSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Data Size", CONCAT(LPAD(REPLACE(
FORMAT(B.ISize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Index Size", CONCAT(LPAD(REPLACE(
FORMAT(B.TSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Table Size" FROM
(SELECT engine,SUM(data_length) DSize,SUM(index_length) ISize,
SUM(data_length+index_length) TSize FROM
information_schema.tables WHERE table_schema NOT IN
('mysql','information_schema','performance_schema') AND
engine IS NOT NULL GROUP BY engine WITH ROLLUP) B,
(SELECT 3 pw) A ORDER BY TSize;
You will see how much wasted space disappeared when migrating the mysqldump to the new 10GB Instance. This will definitely defragment all InnoDB tables. You may need to run the above script (/root/OptimizeAllTables.sql
) I gave you above to run OPTIMIZE TABLE
on all the tables in the signs
database once a week to keep the .ibd
as small as possible. You can also run the Big Storage Engine Space Query to Monitor when it starts approaching 10GB.
You could have asked mysql for all individual table sizes
SELECT table_schema,table_name,data_length,index_length
FROM information_schema.tables
WHERE table_schema NOT IN ('information_schema','mysql');
Summary by Storage Engine
SELECT IFNULL(B.engine,'Total') "Storage Engine",
CONCAT(LPAD(REPLACE(FORMAT(B.DSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Data Size",
CONCAT(LPAD(REPLACE(FORMAT(B.ISize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Index Size",
CONCAT(LPAD(REPLACE(FORMAT(B.TSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Table Size" FROM
(SELECT engine,SUM(data_length) DSize,SUM(index_length) ISize,
SUM(data_length+index_length) TSize FROM information_schema.tables
WHERE table_schema NOT IN ('mysql','information_schema','performance_schema')
AND engine IS NOT NULL GROUP BY engine WITH ROLLUP) B,(SELECT 3 pw) A
ORDER BY TSize;
Summary by Database
SELECT DBName,CONCAT(LPAD(FORMAT(SDSize/POWER(1024,pw),3),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Data Size",
CONCAT(LPAD(FORMAT(SXSize/POWER(1024,pw),3),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Index Size",
CONCAT(LPAD(FORMAT(STSize/POWER(1024,pw),3),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') "Total Size"
FROM (SELECT IFNULL(DB,'All Databases') DBName,SUM(DSize) SDSize,
SUM(XSize) SXSize,SUM(TSize) STSize FROM (SELECT table_schema DB,
data_length DSize,index_length XSize,data_length+index_length TSize
FROM information_schema.tables WHERE table_schema NOT IN
('mysql','information_schema','performance_schema')) AAA
GROUP BY DB WITH ROLLUP) AA,(SELECT 3 pw) BB ORDER BY (SDSize+SXSize);
Summary by Database/Storage Engine
SELECT Statistic,DataSize "Data Size",IndexSize "Index Size",TableSize "Table Size"
FROM (SELECT IF(ISNULL(table_schema)=1,10,0) schema_score,
IF(ISNULL(engine)=1,10,0) engine_score, IF(ISNULL(table_schema)=1,
'ZZZZZZZZZZZZZZZZ',table_schema) schemaname,
IF(ISNULL(B.table_schema)+ISNULL(B.engine)=2,
"Storage for All Databases",IF(ISNULL(B.table_schema)+ISNULL(B.engine)=1,
CONCAT("Storage for ",B.table_schema),CONCAT(B.engine," Tables for ",
B.table_schema))) Statistic,
CONCAT(LPAD(REPLACE(FORMAT(B.DSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') DataSize,
CONCAT(LPAD(REPLACE(FORMAT(B.ISize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') IndexSize,
CONCAT(LPAD(REPLACE(FORMAT(B.TSize/POWER(1024,pw),3),',',''),17,' '),' ',
SUBSTR(' KMGTP',pw+1,1),'B') TableSize FROM (SELECT table_schema,engine,
SUM(data_length) DSize,SUM(index_length) ISize,SUM(data_length+index_length) TSize
FROM information_schema.tables WHERE table_schema NOT IN
('mysql','information_schema','performance_schema') AND engine IS NOT NULL
GROUP BY table_schema,engine WITH ROLLUP) B,(SELECT 3 pw) A) AA
ORDER BY schemaname,schema_score,engine_score;
Please send these queries to your IT people and have them email the results back
Please keep in mind that mysqldumps do not contain indexes. A mysqldump is simply a logical representation of the data plus the commands and directive to crate the table, load the table, and make indexes. What get generated physically upon restore can be known by these queries before launching the mysqldump.
Best Answer
Unfortunately, yes, you'll need to reduce the size of your root LV.
(You could reduce the size of swap, too, but that's already a fairly small volume)
Even if you can use that 4MB, a snapshot of your root volume will become invalid quite quickly when LVM runs out of "free" disk space.
You get prompted with a text box asking how much of your disk to use when you do an Ubuntu install (even if you select "
use entire disk
"). If you're building systems to muck around on, or virtual machines, I recommend setting this to90%
(leaving 10% for LVM) - you probably won't miss the space, and you never know when it'll come in handy.The mechanics of how to shrink the root volume aren't too hard to find on the web, but questions about that are probably best suited to unix.se.
Update: Make sure you don't rely on LVM as your only backup strategy - if you change enough data on disk and your snapshot runs out of free LVM space to use, the snapshot will simply stop working. Using LVM is one of the only ways you can take file-based backups of MySQL (esp. in conjunction with
FLUSH TABLES WITH READ LOCK
) without shutting down the server, though, which is quite handy.