exports.up = async function(knex) { await knex.schema.createTable('users', (table) => { table.increments('id'); table.text('username', 32) .notNullable() .unique(); table.text('email', 32) .notNullable() .unique(); table.text('password') .notNullable(); table.text('name', 32); table.text('bio', 1000); table.specificType('ip', 'inet'); table.datetime('created_at') .notNullable() .defaultTo(knex.fn.now()); }); await knex.schema.createTable('shelves', (table) => { table.increments('id'); table.text('slug') .notNullable(); table.integer('founder_id') .notNullable() .references('id') .inTable('users'); table.datetime('created_at') .notNullable() .defaultTo(knex.fn.now()); }); await knex.schema.createTable('shelves_settings', (table) => { table.increments('id'); table.integer('shelf_id') .primary() .references('id') .inTable('shelves'); table.text('name'); table.text('title'); table.text('description'); table.enum('view_access', ['public', 'registered', 'private']) .notNullable() .defaultTo('public'); table.enum('post_access', ['registered', 'private']) .notNullable() .defaultTo('public'); table.boolean('is_nsfw'); }); await knex.schema.createTable('posts', (table) => { table.increments('id'); table.text('title') .notNullable(); table.text('body'); table.text('url'); table.integer('shelf_id') .notNullable() .references('id') .inTable('shelves'); table.integer('user_id') .notNullable() .references('id') .inTable('users'); table.datetime('created_at') .notNullable() .defaultTo(knex.fn.now()); }); await knex.raw(`ALTER TABLE posts ADD CONSTRAINT post_content CHECK (body IS NOT NULL OR url IS NOT NULL)`); }; exports.down = async function(knex) { await knex.schema.dropTable('posts'); await knex.schema.dropTable('shelves_settings'); await knex.schema.dropTable('shelves'); await knex.schema.dropTable('users'); };