레일즈 마이그레이션에서 검사 제약 조건을 추가하려면 어떻게 해야 합니까?
레일즈 앱의 기존 테이블에 새 정수 열을 추가해야 합니다.열은 값 1, 2, 3만 가질 수 있으므로 표/열에 체크 제약 조건을 추가하려고 합니다.레일즈 마이그레이션 내에서 이 제약 조건을 지정하려면 어떻게 해야 합니까?
레일즈 마이그레이션은 제약 조건을 추가하는 어떤 방법도 제공하지 않지만 마이그레이션을 통해 수행할 수 있지만 실제 SQL을 전달하여 실행()할 수 있습니다.
마이그레이션 파일 만들기:
ruby script/generate Migration AddConstraint
이제 마이그레이션 파일에서 다음을 수행합니다.
class AddConstraint < ActiveRecord::Migration
def self.up
execute "ALTER TABLE table_name ADD CONSTRAINT check_constraint_name CHECK (check_column_name IN (1, 2, 3) )"
end
def self.down
execute "ALTER TABLE table_name DROP CONSTRAINT check_constraint_name"
end
end
레일 6.1+ 구속조건 확인
Rails 6.1은 데이터베이스 마이그레이션에 검사 제약 조건에 대한 기본 지원을 추가했습니다.
이제 정수 열 값을 1, 2, 3으로 제한하는 검사 제약 조건을 추가하기 위한 마이그레이션을 다음과 같이 작성할 수 있습니다.
class AddConstraint < ActiveRecord::Migration
def up
add_check_constraint :table_name, 'check_column_name IN (1, 2, 3)', name: 'check_constraint_name'
end
def down
remove_check_constraint :table_name, name: 'check_constraint_name'
end
end
여기 및 에 대한 자세한 내용을 확인할 수 있는 상대 PR 링크가 있습니다.
마이그레이션 검증자 보석으로 이 작업을 수행할 수 있습니다.자세한 내용은 여기를 참조하십시오. https://github.com/vprokopchuk256/mv-core
이 보석을 사용하면 DB 수준에서 포함 검증을 정의할 수 있습니다.
def change
change_table :table_name do |t|
t.integer :column_name, inclusion: [1, 2, 3]
end
end
또한 유효성 검사를 정의하는 방법과 표시해야 하는 오류 메시지를 정의할 수 있습니다.
def change
change_table :posts do |t|
t.integer :priority,
inclusion: { in: [1, 2, 3],
as: :trigger,
message: "can't be anything else than 1, 2, or 3" }
end
end
마이그레이션에서 모델로 바로 검증 수준을 높일 수도 있습니다.
class Post < ActiveRecord::Base
enforce_migration_validations
end
마이그레이션에서 정의된 검증은 모델의 ActiveModel 검증으로도 정의됩니다.
Post.new(priority: 3).valid?
=> true
Post.new(priority: 4).valid?
=> false
Post.new(priority: 4).errors.full_messages
=> ["Priority can't be anything else than 1, 2, or 3"]
이 답변은 2021년 5월부터 사용되지 않습니다.
나는 방금 이것에 대한 보석을 출판했습니다: active_record-postgres-constraints.README에서 설명하는 것처럼 db/schema.rb 파일과 함께 사용할 수 있으며 마이그레이션에서 다음 방법을 지원합니다.
create_table TABLE_NAME do |t|
# Add columns
t.check_constraint conditions
# conditions can be a String, Array or Hash
end
add_check_constraint TABLE_NAME, conditions
remove_check_constraint TABLE_NAME, CONSTRAINT_NAME
현재 포스트그레스만 지원됩니다.
저는 방금 Postgre를 받는 것을 끝냈습니다.SQL CHECK 제약 조건이 작동합니다.
Nilesh의 솔루션은 완전하지 않습니다. db/schema.rb 파일은 제약 조건을 포함하지 않으므로 db:setup을 사용하는 테스트 및 배포는 제약 조건을 얻지 못합니다.http://guides.rubyonrails.org/migrations.html#types-of-schema-dumps 에 따름
마이그레이션에서 사용자 지정 SQL 문을 실행할 수 있지만 스키마 덤프는 데이터베이스에서 해당 문을 재구성할 수 없습니다.이러한 기능을 사용하는 경우 스키마 형식을 :sql로 설정해야 합니다.
즉, config/application.rb 집합에 있습니다.
config.active_record.schema_format = :sql
불행히도, 만약 당신이 Postgre를 사용한다면,SQL 결과 덤프를 로드할 때 오류가 발생할 수 있습니다. 오류: 언어 plpgsql의 소유자여야 합니다.저는 포스트그리로 가고 싶지 않았습니다.해당 토론의 SQL 구성 경로. 또한 어떤 경우에도 읽을 수 있는 db/schema.rb 파일이 좋습니다.따라서 마이그레이션 파일에서 사용자 지정 SQL은 제외되었습니다.
Valera가 제안한 https://github.com/vprokopchuk256/mv-core 보석은 유망한 것처럼 보이지만 제한된 제약 조건만을 지원합니다. (그리고 그것을 사용하려고 할 때 오류가 발생했습니다. 비록 그것은 제가 포함하고 있는 다른 보석과의 비호환성 때문일 수도 있습니다.)
제가 함께 했던 해결책(해킹)은 모델 코드가 제약 조건을 삽입하도록 하는 것입니다.검증과 같은 것이기 때문에 여기에 설명합니다.
class MyModel < ActiveRecord::Base
validates :my_constraint
def my_constraint
unless MyModel.connection.execute("SELECT * FROM information_schema.check_constraints WHERE constraint_name = 'my_constraint'").any?
MyModel.connection.execute("ALTER TABLE my_models ADD CONSTRAINT my_constraint CHECK ( ...the SQL expression goes here ... )")
end
end
물론 각 검증 전에 추가로 선택합니다. 문제가 있다면 레일을 사용하여 오라클에 연결한 후 특정 스크립트를 실행하는 방법에 설명된 것과 같은 "연결 후" 원숭이 패치에 추가하는 것이 솔루션입니다. (검증/제약 추가는 트랜잭션 내에서 발생하므로 선택 결과를 단순히 캐시할 수 없습니다.)이온이 롤백될 수 있으므로 매번 확인해야 합니다.)
사용할 수 있습니다.Sequel
보석 https://github.com/jeremyevans/sequel
Sequel.migration do
change do
create_table(:artists) do
primary_key :id
String :name
constraint(:name_min_length){char_length(name) > 2}
end
end
end
언급URL : https://stackoverflow.com/questions/4664520/how-do-i-add-a-check-constraint-in-a-rails-migration
'programing' 카테고리의 다른 글
Tomcat에서 메모리 누수가 발생할 가능성이 매우 높은가요? (0) | 2023.07.28 |
---|---|
Oracle 'printf' 등가 (0) | 2023.07.28 |
C - 직렬화 기술 (0) | 2023.07.28 |
데이터 프레임 인덱스에 함수 적용 (0) | 2023.07.28 |
조각에서 활동 메서드 호출 (0) | 2023.07.28 |