I'm creating an open source stack exchange clone and the following is my schema. What should I add indexes on for it to be optimal?
Here is the schema in Rails format (SQL format below as well):
create_table "comments", force: true do |t|
t.integer "id"
t.integer "post_id", null: false
t.integer "user_id", null: false
t.text "body", null: false
t.integer "score", default: 0, null: false
t.datetime "created_at"
t.datetime "updated_at"
end
create_table "post_types", force: true do |t|
t.integer "id"
t.string "name", null: false
end
create_table "posts", force: true do |t|
t.integer "id"
t.integer "post_type_id", limit: 2, null: false
t.integer "accepted_answer_id"
t.integer "parent_id"
t.integer "user_id", null: false
t.text "title", limit: 255, null: false
t.text "body", null: false
t.integer "score", default: 0, null: false
t.integer "views", default: 1, null: false
t.datetime "created_at"
t.datetime "updated_at"
end
create_table "posts_tags", force: true do |t|
t.integer "id"
t.integer "post_id", null: false
t.integer "tag_id", null: false
end
create_table "tag_synonyms", force: true do |t|
t.integer "id"
t.string "source_tag", null: false
t.string "synonym", null: false
end
create_table "tags", force: true do |t|
t.integer "id"
t.string "name", null: false
end
create_table "users", force: true do |t|
t.integer "id"
t.string "first_name", limit: 50
t.string "last_name", limit: 50
t.string "display_name", limit: 100, null: false
t.string "email", limit: 100, null: false
t.string "password", null: false
t.string "salt", null: false
t.string "about_me"
t.string "website_url"
t.string "location", limit: 100
t.integer "karma", default: 0, null: false
t.datetime "created_at"
t.datetime "updated_at"
end
create_table "vote_types", force: true do |t|
t.integer "id"
t.string "name", null: false
end
create_table "votes", force: true do |t|
t.integer "id"
t.integer "post_id", null: false
t.integer "vote_type_id", null: false
t.integer "user_id", null: false
t.datetime "created_at"
t.datetime "updated_at"
end
Here is the raw structure in SQL as well:
CREATE TABLE `comments` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`post_id` int(11) NOT NULL,
`user_id` int(11) NOT NULL,
`body` text NOT NULL,
`score` int(11) NOT NULL DEFAULT '0',
`created_at` datetime DEFAULT NULL,
`updated_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `post_types` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `posts` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`post_type_id` smallint(6) NOT NULL,
`accepted_answer_id` int(11) DEFAULT NULL,
`parent_id` int(11) DEFAULT NULL,
`user_id` int(11) NOT NULL,
`title` tinytext NOT NULL,
`body` text NOT NULL,
`score` int(11) NOT NULL DEFAULT '0',
`views` int(11) NOT NULL DEFAULT '1',
`created_at` datetime DEFAULT NULL,
`updated_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `posts_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`post_id` int(11) NOT NULL,
`tag_id` int(11) NOT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `tag_synonyms` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`source_tag` varchar(255) NOT NULL,
`synonym` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `users` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`first_name` varchar(50) DEFAULT NULL,
`last_name` varchar(50) DEFAULT NULL,
`display_name` varchar(100) NOT NULL,
`email` varchar(100) NOT NULL,
`password` varchar(255) NOT NULL,
`salt` varchar(255) NOT NULL,
`about_me` varchar(255) DEFAULT NULL,
`website_url` varchar(255) DEFAULT NULL,
`location` varchar(100) DEFAULT NULL,
`karma` int(11) NOT NULL DEFAULT '0',
`created_at` datetime DEFAULT NULL,
`updated_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `vote_types` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);
CREATE TABLE `votes` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`post_id` int(11) NOT NULL,
`vote_type_id` int(11) NOT NULL,
`user_id` int(11) NOT NULL,
`created_at` datetime DEFAULT NULL,
`updated_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
);