const team_size_trigger = ` CREATE OR REPLACE FUNCTION enforce_team_size() RETURNS trigger AS $$ DECLARE team_size INTEGER := 3; team_count INTEGER := 0; BEGIN IF (TG_OP = 'UPDATE' OR TG_OP = 'INSERT') THEN SELECT INTO team_count COUNT(id) FROM constructs WHERE account = NEW.account AND team = true; ELSIF (TG_OP = 'DELETE') THEN SELECT INTO team_count COUNT(id) FROM constructs WHERE account = OLD.account AND team = true; END IF; IF team_count != team_size THEN RAISE EXCEPTION 'You must have exactly % constructs in your team.', team_size; END IF; RETURN NEW; END; $$ LANGUAGE plpgsql; CREATE CONSTRAINT TRIGGER check_team_size AFTER INSERT OR UPDATE OR DELETE ON constructs DEFERRABLE INITIALLY DEFERRED FOR EACH ROW EXECUTE PROCEDURE enforce_team_size(); `; exports.up = async knex => { await knex.schema.createTable('constructs', table => { table.uuid('id').primary(); table.timestamps(true, true); table.uuid('account').notNullable() table.foreign('account') .references('id') .inTable('accounts') .onDelete('CASCADE'); table.binary('data').notNullable(); table.boolean('team') .notNullable() .defaultTo(false); }); await knex.raw(team_size_trigger); return true; }; exports.down = async () => {};