MYSQL query Alter table engine only if engine not innodb - mysql

I would like to run one query that alter table's engine (ALTER TABLE table1 ENGINE = INNODB) only if the current engine is not INNODB.
How can I do that?
Update:
I got a case of a query trying to alter the table's engine while its already innodb.

You can use
ALTER TABLE t ENGINE = InnoDB;
You can use this query. If db engine already InnoDB then nothing will happen.
Output will be
MySQL returned an empty result set (i.e. zero rows)
if engine not in InnoDB, then it will convert to InnoDB.

The command has no effect if the table is already on InnoDB.
You can query the table engine from information_schema:
SELECT `ENGINE` from `information_schema`.`TABLES`
WHERE `TABLE_SCHEMA`='my_schema' AND `TABLE_NAME`='table1';

http://mysql.rjweb.org/doc.php/myisam2innodb#generating_alters provides several tips about converting from MyISAM to InnoDB, including:
To generate all the ALTERs to convert all the MyISAM tables to InnoDB:
SELECT CONCAT('USE ', table_schema, '; ALTER TABLE ', table_name, ' ENGINE=InnoDB;')
FROM information_schema.tables
WHERE engine = 'MyISAM'
AND table_schema NOT IN ('mysql', 'information_schema', 'performance_schema');
Then copy and paste the output into the mysql commandline tool.

Related

Delete all data from multiple tables in mysql

I have a db with 100 tables. I want to delete data from all tables using mysql command or in phpmyadmin
Backup your database structure (use mysqldump with --no-data command line option).
Drop database.
Restore database from the dump.
This method have no problems with FOREIGN KEY relations. Rather than DELETE/TRUNCATE usage where you must clear the tables content in definite order (if you'd clear master table before slave one then the deletion will fail due to referential constraint violation).
Use information_schema.TABLES make dynamic query and exeute.
select concat('delete from ',TABLE_NAME,';') from information_schema.TABLES where TABLE_SCHEMA='databasename';
or try this one
SET FOREIGN_KEY_CHECKS = 0;
SET #TABLES = NULL;
SELECT GROUP_CONCAT('delete from ', table_name,';') INTO #TABLES FROM information_schema.tables
WHERE table_schema = 'databasename' and table_name in ('tbl_audit_trail','tbl_celery');
SET #TABLES= replace( #TABLES,',','');
select #TABLES;
copy the result and execute

How do I check if table exists before alter table

I need query to update all tables and set ENGINE = INNODB To many databases. But some of the databases don't have all the same tables; some databases have more tables than others.
So the problem is that
ALTER TABLE `ads` ENGINE = INNODB;
ALTER TABLE `modules` ENGINE = INNODB;
ALTER TABLE `ad_extras` ENGINE = INNODB;
Throws an error when the table modules doe snot exist. I see that I cannot make a direct IF statement' I tried:
IF EXISTS (SHOW TABLES LIKE 'modules') BEGIN
ALTER TABLE `modules` ENGINE = INNODB;
END IF
But it throws
Unrecognized statement type (near IF EXISTS)
Any ideas?
If this is just an ad-hoc task,
select concat('ALTER ', TABLE_NAME, " ENGINE = INNODB;")
from information_schema.TABLES
where TABLE_SCHEMA = '<your schema>';
Execute the output again.
If Exists works only in a stored procedure.
a fixed edition of Jacob's answer:
SET SESSION group_concat_max_len = 1000000;
select group_concat(concat('ALTER Table ', TABLE_NAME, ' ENGINE = INNODB;') SEPARATOR '\n')
from information_schema.TABLES
where TABLE_SCHEMA = 'your_schema_name' and TABLE_TYPE<>'VIEW';
This will give you a script to copy and run separately.
What about testing it simple as this query :
DROP TABLE IF EXISTS `yourtablename`;

ALTER TABLE ALL TABLES ROW_FORMAT=Fixed;

How can I run a command for all tables in a database?
ALTER TABLE table_name ROW_FORMAT=Fixed;
I have more than 40000 tables, I want to change them all in one go.
You cannot alter table more than one table per ALTER statement; but you can use a query on information_schema.tables to generate the alter statements.
Something like
SELECT CONCAT('ALTER TABLE `', table_name, '` ROW_FORMAT=fixed;') AS aQuery
FROM information_schema.tables
WHERE table_schema = 'myschema'
Keep in mind FIXED is not supported for InnoDB tables, and I am not 100% sure if it can even be explicitly set for MyISAM ones (or is entirely dependent on the table's columns' data types.)

can mysql.user table's engine be converted from MyISAM to InnoDb?

I ran the following query on my production MySQL database:
SELECT CONCAT('`', table_schema,'`.`', table_name, '`') AS schema_tables
FROM information_schema.tables AS tb
WHERE `ENGINE` = 'MyISAM'
AND `TABLE_TYPE` = 'BASE TABLE'
ORDER BY table_name DESC;
It returned all the tables from mysql schema, some of them are:
`mysql`.`user`
`mysql`.`time_zone_transition_type`
`mysql`.`time_zone_transition`
`mysql`.`time_zone_name`
`mysql`.`time_zone_leap_second`
`mysql`.`time_zone`
`mysql`.`tables_priv`
`mysql`.`servers`
`mysql`.`proxies_priv`
...
My queries are:
1. Can these be converted to innodb safely?
2. Why were they in MyISAM engine in the first place? Did I change it by mistake or were they default?
Server version: 5.6.22-log MySQL Community Server (GPL)
PS: I know InnoDb is default engine from 5.6 and I never ran any query to convert to MyISAM.
No, you can't!
As the docs say:
Important
Do not convert MySQL system tables in the mysql database (such as user or host) to the InnoDB type. This is an unsupported operation. The system tables must always be of the MyISAM type.

Convert MyISAM to InnoDB database

I'm trying to convert a whole database from MyISAM to InnoDB with this statement:
use information_schema;
SELECT CONCAT('ALTER TABLE ',table_schema,'.',table_name,' ENGINE=InnoDB;')
FROM information_schema.tables
WHERE engine = "MyISAM" AND table_type = "BASE TABLE" AND table_schema = "database";
and while I get a result that every table is changed for example:
ALTER TABLE database.action ENGINE=InnoDB;
when I check the table engines they're still MyISAM. The weird thing is that if I run the command separately
ALTER TABLE action ENGINE='InnoDB';
it works fine for that table.
Any tips on how to do the conversion for the whole database?
The SELECT statement you are running only generates strings; the strings it generates are not being executed as SQL statements. You'd need to take the resultset from that query, and then actually execute those statements as a separate step.