Featured post
Really Slow MySQL Insert Query -
i've got table half million records in it. it's not huge. couple varchar(255) fields, ints, float, , couple timestamps. there indices on ints foreign key constraints. inserts taking forever. i'm talking 1-4 seconds insert one row. i've had deal slow select queries plenty of times, i'm stuck trying figure out what's going on insert.
edit: okay, asking ideas on how debug this, but, here's tables involved. inserting "ingredients" takes forever. throwing portion of schema onto web doesn't bite me later...
create table `ingredients` ( `id` int(11) not null auto_increment, `quantity` float default null, `food` varchar(255) not null, `unit_id` int(11) default null, `ingredient_group_id` int(11) default null, `order_by` int(11) not null, `created_at` datetime not null, `updated_at` datetime not null, `description` varchar(255) default null, `range` float default null, primary key (`id`), key `unit_id` (`unit_id`), key `ingredient_group_id` (`ingredient_group_id`), constraint `ingredients_ibfk_1` foreign key (`unit_id`) references `units` (`id`), constraint `ingredients_ibfk_2` foreign key (`ingredient_group_id`) references `ingredient_groups` (`id`) on delete cascade ) engine=innodb auto_increment=269974 default charset=utf8 create table `units` ( `id` int(11) not null auto_increment, `name` varchar(255) not null, `abbreviation` varchar(255) character set latin1 not null, `type` int(11) not null, `si` float not null, `lower_bound` float default null, `lower_unit_id` int(11) default null, `upper_bound` float default null, `upper_unit_id` int(11) default null, primary key (`id`), key `lower_unit_id` (`lower_unit_id`), key `upper_unit_id` (`upper_unit_id`), constraint `units_ibfk_1` foreign key (`lower_unit_id`) references `units` (`id`), constraint `units_ibfk_2` foreign key (`upper_unit_id`) references `units` (`id`) ) engine=innodb auto_increment=14 default charset=utf8 create table `ingredient_groups` ( `id` int(11) not null auto_increment, `name` varchar(255) default null, `recipe_id` int(11) not null, `order_by` int(11) not null, `created_at` datetime not null, `updated_at` datetime not null, primary key (`id`), key `recipe_id` (`recipe_id`), constraint `ingredient_groups_ibfk_1` foreign key (`recipe_id`) references `recipes` (`id`) on delete cascade ) engine=innodb auto_increment=32739 default charset=utf8
lots of information missing, things i'd check first:
if on myisam tables: extremely fragmented files, index files. use
filefrag
check that. can happen if database grew time. if so, shut down mysql, copy database directory, rename original , new copies , restart mysqlif use innodb tables: file-based datastore, again fragmented. in case, fragmentation can both @ filesystem level (check , handle above) or @ datastore level, use innodb tools. in worst case block-device-based datastore (which can't externally fragmented) can exhibit bad case of internal fragmentation.
some index extremely low cardinality. is, non-unique index few distinct values present, is, lots of repeats. indexes approach asymptotically linear list, o(n) time profiles. can either index on table or referred foreign index.
reader contention. unlikely, huge number of concurrent readers can stall single writer.
edit:
after reading definitions, think ingredients.unit_id
, ingredients.ingredient_group_id
first candidates check, since seem have low cardinality.
the first 1 unlikely useful (do plan select ingredients measured in spoons?), can drop it.
the second 1 can useful; if there few ingredient groups, cardinality can low, degrading performance. raise cardinality, add part make more discriminating. if no other field appear in query group id, add main id or creation date, making (ingredient_group_id, id)
or (ingredient_group_id, created_at)
. seems counterintuitive add complexity make faster, can help. bonus, can add sort created_at
query selects ingredient_group_id
without performance penalty.
- Get link
- X
- Other Apps
Comments
Post a Comment