Heroku 迁移失败 UndefinedTable 错误
Heroku migration fails UndefinedTable Error
我在开发和测试中使用 sqlite,并部署到在生产中使用 Postgres 的 Heroku。我通过 运行 在终端中执行以下命令为 'Reviews' 创建了一个新模型:
rails g model Review comment:text star:integer room:references reservation:references guest:references host:references type
rails g model GuestReview --parent=Review --migration=false
rails g model HostReview --parent=Review --migration=false
rails db:migrate
这是上述命令的输出:
$ rails g model Review comment:text star:integer room:references reservation:references guest:references host:references type
Running via Spring preloader in process 6862
invoke active_record
create db/migrate/20180613031058_create_reviews.rb
create app/models/review.rb
invoke test_unit
create test/models/review_test.rb
create test/fixtures/reviews.yml
$ rails g model GuestReview --parent=Review --migration=false
Running via Spring preloader in process 6872
invoke active_record
create app/models/guest_review.rb
invoke test_unit
create test/models/guest_review_test.rb
create test/fixtures/guest_reviews.yml
$ rails g model HostReview --parent=Review --migration=false
Running via Spring preloader in process 6880
invoke active_record
create app/models/host_review.rb
invoke test_unit
create test/models/host_review_test.rb
create test/fixtures/host_reviews.yml
$ rails db:migrate
== 20180613031058 CreateReviews: migrating
====================================
-- create_table(:reviews)
-> 0.0806s
== 20180613031058 CreateReviews: migrated (0.0828s)
===========================
该网站在本地主机上正常运行,当我在 sqlite 中检查数据时,我能够正确保存评论。当我部署到 Heroku 和 运行
heroku run rake db:migrate
我收到以下错误:
rails aborted!
StandardError: An error has occurred, this and all later migrations canceled:
PG::UndefinedTable: ERROR: relation "guests" does not exist
: CREATE TABLE "reviews" ("id" serial primary key, "comment" text,
"star" integer DEFAULT 1, "room_id" integer, "reservation_id" integer,
"guest_id" integer, "host_id" integer, "type" character varying,
"created_at" timestamp NOT NULL, "updated_at" timestamp NOT NULL,
CONSTRAINT "fk_rails_b98b7304fe"
FOREIGN KEY ("room_id")
REFERENCES "rooms" ("id")
, CONSTRAINT "fk_rails_628a43e51f"
FOREIGN KEY ("reservation_id")
REFERENCES "reservations" ("id")
, CONSTRAINT "fk_rails_eaa1ce2871"
FOREIGN KEY ("guest_id")
REFERENCES "guests" ("id")
, CONSTRAINT "fk_rails_ac5cb4d097"
FOREIGN KEY ("host_id")
REFERENCES "hosts" ("id")
)
这是评论的迁移文件:
class CreateReviews < ActiveRecord::Migration[5.0]
def change
create_table :reviews do |t|
t.text :comment
t.integer :star, default: 1
t.references :room, foreign_key: true
t.references :reservation, foreign_key: true
t.references :guest, foreign_key: true
t.references :host, foreign_key: true
t.string :type
t.timestamps
end
end
end
评论模型如下:
class Review < ApplicationRecord
end
这里是 guest_review 模型:
class GuestReview < Review
belongs_to :guest, class_name: "User"
end
这里是 host_review 模型:
class HostReview < Review
belongs_to :host, class_name: "User"
end
它在 Heroku Postgres 上似乎正在寻找不存在的客人 table。有没有办法解决此错误,使其在我的开发环境和 Heroku 中正常运行?
在迁移中,t.references :guest, foreign_key: true
做两件事:
- 它创建一个名为
guest_id
. 的整数列(或 bigint
,具体取决于您的 Rails 版本)
- 它在
guests
table. 中的guest_id
列到id
列添加了数据库内部的外键约束
但是您要引用的 table 是 users
(即 User
模型),而不是 guests
。由于名称不匹配,您必须调整 t.references
调用以告诉 ActiveRecord 要引用哪个 table:
t.references :guest, foreign_key: { to_table: :users }
对于无法推断 table 名称的任何其他 t.references
调用类似。
解决眼前的问题后,您确实应该在开发环境中安装 PostgreSQL,以便您可以在同一个堆栈上进行开发、测试和部署。除了最简单和最琐碎的事情之外,ActiveRecord 不提供数据库可移植性,因此使用不同的数据库进行开发和部署是灾难的根源。
我在开发和测试中使用 sqlite,并部署到在生产中使用 Postgres 的 Heroku。我通过 运行 在终端中执行以下命令为 'Reviews' 创建了一个新模型:
rails g model Review comment:text star:integer room:references reservation:references guest:references host:references type
rails g model GuestReview --parent=Review --migration=false
rails g model HostReview --parent=Review --migration=false
rails db:migrate
这是上述命令的输出:
$ rails g model Review comment:text star:integer room:references reservation:references guest:references host:references type
Running via Spring preloader in process 6862
invoke active_record
create db/migrate/20180613031058_create_reviews.rb
create app/models/review.rb
invoke test_unit
create test/models/review_test.rb
create test/fixtures/reviews.yml
$ rails g model GuestReview --parent=Review --migration=false
Running via Spring preloader in process 6872
invoke active_record
create app/models/guest_review.rb
invoke test_unit
create test/models/guest_review_test.rb
create test/fixtures/guest_reviews.yml
$ rails g model HostReview --parent=Review --migration=false
Running via Spring preloader in process 6880
invoke active_record
create app/models/host_review.rb
invoke test_unit
create test/models/host_review_test.rb
create test/fixtures/host_reviews.yml
$ rails db:migrate
== 20180613031058 CreateReviews: migrating
====================================
-- create_table(:reviews)
-> 0.0806s
== 20180613031058 CreateReviews: migrated (0.0828s)
===========================
该网站在本地主机上正常运行,当我在 sqlite 中检查数据时,我能够正确保存评论。当我部署到 Heroku 和 运行
heroku run rake db:migrate
我收到以下错误:
rails aborted!
StandardError: An error has occurred, this and all later migrations canceled:
PG::UndefinedTable: ERROR: relation "guests" does not exist
: CREATE TABLE "reviews" ("id" serial primary key, "comment" text,
"star" integer DEFAULT 1, "room_id" integer, "reservation_id" integer,
"guest_id" integer, "host_id" integer, "type" character varying,
"created_at" timestamp NOT NULL, "updated_at" timestamp NOT NULL,
CONSTRAINT "fk_rails_b98b7304fe"
FOREIGN KEY ("room_id")
REFERENCES "rooms" ("id")
, CONSTRAINT "fk_rails_628a43e51f"
FOREIGN KEY ("reservation_id")
REFERENCES "reservations" ("id")
, CONSTRAINT "fk_rails_eaa1ce2871"
FOREIGN KEY ("guest_id")
REFERENCES "guests" ("id")
, CONSTRAINT "fk_rails_ac5cb4d097"
FOREIGN KEY ("host_id")
REFERENCES "hosts" ("id")
)
这是评论的迁移文件:
class CreateReviews < ActiveRecord::Migration[5.0]
def change
create_table :reviews do |t|
t.text :comment
t.integer :star, default: 1
t.references :room, foreign_key: true
t.references :reservation, foreign_key: true
t.references :guest, foreign_key: true
t.references :host, foreign_key: true
t.string :type
t.timestamps
end
end
end
评论模型如下:
class Review < ApplicationRecord
end
这里是 guest_review 模型:
class GuestReview < Review
belongs_to :guest, class_name: "User"
end
这里是 host_review 模型:
class HostReview < Review
belongs_to :host, class_name: "User"
end
它在 Heroku Postgres 上似乎正在寻找不存在的客人 table。有没有办法解决此错误,使其在我的开发环境和 Heroku 中正常运行?
在迁移中,t.references :guest, foreign_key: true
做两件事:
- 它创建一个名为
guest_id
. 的整数列(或 - 它在
guests
table. 中的
bigint
,具体取决于您的 Rails 版本)
guest_id
列到id
列添加了数据库内部的外键约束
但是您要引用的 table 是 users
(即 User
模型),而不是 guests
。由于名称不匹配,您必须调整 t.references
调用以告诉 ActiveRecord 要引用哪个 table:
t.references :guest, foreign_key: { to_table: :users }
对于无法推断 table 名称的任何其他 t.references
调用类似。
解决眼前的问题后,您确实应该在开发环境中安装 PostgreSQL,以便您可以在同一个堆栈上进行开发、测试和部署。除了最简单和最琐碎的事情之外,ActiveRecord 不提供数据库可移植性,因此使用不同的数据库进行开发和部署是灾难的根源。