问题描述
我想从这里出发:
schema "products" do
field :name,:string
field :brand,:string
...more fields...
end
对此:
schema "products" do
field :name,:string
...more fields...
end
schema "brands" do
field :name,:string
...more fields...
end
schema "product_brand_joins" do
field :p_id,:integer
field :b_id,:integer
...more fields...
end
在不丢失具有包含:brand字段字符串的产品的当前数据的情况下。
我了解如何创建新的brands表和product_brand_joins表,以及如何通过ecto迁移从product表中删除“:brand”。但是有没有办法将我当前的数据处理到新表中?
解决方法
您可以使用execute/1
或 function setErrorFor(input,message) {
const formControl = input.parentElement; // .form-control
const small = formControl.querySelector('small');
// add error message inside small
small.innerText = message;
// add errror class
formControl.className = 'form-control error';
}
函数执行SQL语句,其中接受两个参数的是第一个的可回滚版本,该版本希望语句在迁移时执行,而一个在执行回滚时。
因此,您可以使用它来定义迁移时应该发生的事情,这成为定义语句的问题。 this docs page from PostgreSQL的末尾有一个基于子查询插入的示例,我们将在此处使用它。
在您的迁移execute/2
文件中:
.exs
然后对于回滚,您将在迁移中实现use Ecto.Migration
def up do
create table(:brands) do
add :name,:string,# add other fields
end
create table("product_brand_joins") do
add :product_id,references: :products
add :brand_id,references: :brands
end
# Insert into the brands table a brand with each name found in products
execute(
"INSERT INTO brands(name)
SELECT DISTINCT(brand) FROM products"
)
# Insert into the joined table the product and brand ids
execute(
"INSERT INTO product_brand_joins(product_id,brand_id)
SELECT p.id,b.id FROM products p LEFT JOIN brands b ON p.brand = b.name"
)
# And finally delete the column from products
alter table(:products) do
remove :brand
end
end
函数,以使用类似的逻辑来还原该过程:在down
中创建brand列,并根据相应的品牌名称进行填充在产品ID上,然后删除新表。