为什么我的 Knex 迁移在 Heroku 上失败,但在本地却没有?
Why does my Knex migration fail on Heroku but not locally?
我正在尝试在 Heroku 上部署我的第一个 React 应用程序,在我开始迁移之前一切似乎都运行良好。我的 Knex 迁移在本地运行良好,但是当我尝试在 Heroku 上 运行 时,迁移失败。
由于在我的本地计算机上 运行 时它工作正常,这是我第一次尝试部署任何东西,我不确定如何调试它。
这是我的迁移代码:
exports.up = function(knex, Promise) {
return Promise.all([
// USERS TABLE
knex.schema.createTable('users', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('name').notNullable();
t.string('email')
.unique()
.notNullable();
t.string('password').notNullable();
t.timestamp('joined', { useTz: false }).notNullable();
t.text('website');
t.string('github');
t.string('twitter');
t.text('avatar');
t.boolean('is_admin')
.defaultTo(false)
.notNullable();
}),
// INSTRUCTORS TABLE
knex.schema.createTable('instructors', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('name')
.unique()
.notNullable();
t.timestamp('created', { useTz: false }).notNullable();
t.text('website');
t.string('github');
t.string('twitter');
t.text('avatar');
}),
// TUTORIALS TABLE
knex.schema.createTable('tutorials', t => {
t.string('id')
.primary()
.unique()
.notNullable();
t.uuid('user_id').notNullable();
t.uuid('instructor_id');
t.string('instructor_name');
t.string('title').notNullable();
t.text('url')
.unique()
.notNullable();
t.timestamp('date', { useTz: false }).notNullable();
t.enum('cost', ['free', 'paid']).notNullable();
t.enum('medium', ['article', 'video']).notNullable();
t.enum('difficulty', ['beginner', 'advanced']).notNullable();
t.specificType('categories', 'text ARRAY').notNullable();
}),
// COMMENTS TABLE
knex.schema.createTable('comments', t => {
t.string('id')
.primary()
.unique()
.notNullable();
t.uuid('user_id').notNullable();
t.string('tutorial_id').notNullable();
t.text('body').notNullable();
t.timestamp('date', { useTz: false }).notNullable();
}),
knex.schema.createTable('tutorial_votes', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('tutorial_id').notNullable();
t.uuid('user_id').notNullable();
t.smallint('vote_value');
}),
knex.schema.createTable('comment_votes', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('comment_id').notNullable();
t.uuid('user_id').notNullable();
t.smallint('vote_value');
}),
knex.schema.createTable('favorites', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('tutorial_id').notNullable();
t.uuid('user_id').notNullable();
t.timestamp('date', { useTz: false }).notNullable();
})
]);
console.log('Tables created successfully');
};
exports.down = function(knex, Promise) {
return Promise.all([
knex.schema.dropTable('users'),
knex.schema.dropTable('instructors'),
knex.schema.dropTable('tutorials'),
knex.schema.dropTable('comments'),
knex.schema.dropTable('tutorial_votes'),
knex.schema.dropTable('comment_votes'),
knex.schema.dropTable('favorites')
]);
console.log('Tables dropped');
};
这是我得到的错误:
remote: migration file "20190731184441_setup.js" failed
remote: migration failed with error: Cannot read property 'all' of undefined
remote: TypeError: Cannot read property 'all' of undefined
remote: at Object.exports.up (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/db/migrations/20190731184441_setup.js:2:18)
remote: at Object.<anonymous> (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/lib/migrate/Migrator.js:503:40)
remote: at Object.tryCatcher (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/util.js:16:23)
remote: at Promise._settlePromiseFromHandler (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:547:31)
remote: at Promise._settlePromise (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:604:18)
remote: at Promise._settlePromiseCtx (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:641:10)
remote: at _drainQueueStep (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:97:12)
remote: at _drainQueue (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:86:9)
remote: at Async._drainQueues (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:102:5)
remote: at Immediate.Async.drainQueues [as _onImmediate] (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:15:14)
remote: at processImmediate (internal/timers.js:439:21)
已通过从 exports.up = function(knex, Promise)
和 exports.down = function(knex, Promise)
中删除 Promise
来修复
我认为这可能是您本地安装的版本与 Heroku 安装的版本不匹配。如果您的 semver 规范非常宽松,那将允许 Heroku 安装更新的版本,并且您可能已经针对本地版本进行了一段时间的开发。
我怀疑的原因:Knex switched to native promises 版本 0.18.0,这意味着迁移不再通过 Bluebird Promise
。该参数不再存在,因此您的错误。
我正在尝试在 Heroku 上部署我的第一个 React 应用程序,在我开始迁移之前一切似乎都运行良好。我的 Knex 迁移在本地运行良好,但是当我尝试在 Heroku 上 运行 时,迁移失败。
由于在我的本地计算机上 运行 时它工作正常,这是我第一次尝试部署任何东西,我不确定如何调试它。
这是我的迁移代码:
exports.up = function(knex, Promise) {
return Promise.all([
// USERS TABLE
knex.schema.createTable('users', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('name').notNullable();
t.string('email')
.unique()
.notNullable();
t.string('password').notNullable();
t.timestamp('joined', { useTz: false }).notNullable();
t.text('website');
t.string('github');
t.string('twitter');
t.text('avatar');
t.boolean('is_admin')
.defaultTo(false)
.notNullable();
}),
// INSTRUCTORS TABLE
knex.schema.createTable('instructors', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('name')
.unique()
.notNullable();
t.timestamp('created', { useTz: false }).notNullable();
t.text('website');
t.string('github');
t.string('twitter');
t.text('avatar');
}),
// TUTORIALS TABLE
knex.schema.createTable('tutorials', t => {
t.string('id')
.primary()
.unique()
.notNullable();
t.uuid('user_id').notNullable();
t.uuid('instructor_id');
t.string('instructor_name');
t.string('title').notNullable();
t.text('url')
.unique()
.notNullable();
t.timestamp('date', { useTz: false }).notNullable();
t.enum('cost', ['free', 'paid']).notNullable();
t.enum('medium', ['article', 'video']).notNullable();
t.enum('difficulty', ['beginner', 'advanced']).notNullable();
t.specificType('categories', 'text ARRAY').notNullable();
}),
// COMMENTS TABLE
knex.schema.createTable('comments', t => {
t.string('id')
.primary()
.unique()
.notNullable();
t.uuid('user_id').notNullable();
t.string('tutorial_id').notNullable();
t.text('body').notNullable();
t.timestamp('date', { useTz: false }).notNullable();
}),
knex.schema.createTable('tutorial_votes', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('tutorial_id').notNullable();
t.uuid('user_id').notNullable();
t.smallint('vote_value');
}),
knex.schema.createTable('comment_votes', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('comment_id').notNullable();
t.uuid('user_id').notNullable();
t.smallint('vote_value');
}),
knex.schema.createTable('favorites', t => {
t.uuid('id')
.primary()
.unique()
.notNullable();
t.string('tutorial_id').notNullable();
t.uuid('user_id').notNullable();
t.timestamp('date', { useTz: false }).notNullable();
})
]);
console.log('Tables created successfully');
};
exports.down = function(knex, Promise) {
return Promise.all([
knex.schema.dropTable('users'),
knex.schema.dropTable('instructors'),
knex.schema.dropTable('tutorials'),
knex.schema.dropTable('comments'),
knex.schema.dropTable('tutorial_votes'),
knex.schema.dropTable('comment_votes'),
knex.schema.dropTable('favorites')
]);
console.log('Tables dropped');
};
这是我得到的错误:
remote: migration file "20190731184441_setup.js" failed
remote: migration failed with error: Cannot read property 'all' of undefined
remote: TypeError: Cannot read property 'all' of undefined
remote: at Object.exports.up (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/db/migrations/20190731184441_setup.js:2:18)
remote: at Object.<anonymous> (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/lib/migrate/Migrator.js:503:40)
remote: at Object.tryCatcher (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/util.js:16:23)
remote: at Promise._settlePromiseFromHandler (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:547:31)
remote: at Promise._settlePromise (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:604:18)
remote: at Promise._settlePromiseCtx (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/promise.js:641:10)
remote: at _drainQueueStep (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:97:12)
remote: at _drainQueue (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:86:9)
remote: at Async._drainQueues (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:102:5)
remote: at Immediate.Async.drainQueues [as _onImmediate] (/tmp/build_7917ecdef592ca80a65bfdee9b4e67c6/server/node_modules/knex/node_modules/bluebird/js/release/async.js:15:14)
remote: at processImmediate (internal/timers.js:439:21)
已通过从 exports.up = function(knex, Promise)
和 exports.down = function(knex, Promise)
Promise
来修复
我认为这可能是您本地安装的版本与 Heroku 安装的版本不匹配。如果您的 semver 规范非常宽松,那将允许 Heroku 安装更新的版本,并且您可能已经针对本地版本进行了一段时间的开发。
我怀疑的原因:Knex switched to native promises 版本 0.18.0,这意味着迁移不再通过 Bluebird Promise
。该参数不再存在,因此您的错误。