2014-03-19 3 views
1

을 사용하여 복잡한 업데이트 문 작성과 같이 from 절을 사용하여 업데이트 문을 작성하기 위해 Arel::UpdateManager을 사용하는 예를 찾고 couldn.t을 찾았습니다. 내가 본 것처럼, Arel::UpdateManager 초기화시 주 엔진을 설정하고 업데이트 할 다양한 필드와 값을 설정할 수 있습니다. 실제로이 작업을 수행 할 수있는 방법이 있습니까?AREL : from 부속 절

또 다른 방법은 Postgres posix 정규식을 ARel에 표현하는 방법을 찾는 것입니다.하지만 지금은 불가능할 수 있습니다.

답변

1

지금까지 arel 보석의 현재 버전이 표시되지 않습니다. 에서 검색어에 대한 키워드를 지원합니다.

:

UPDATE t SET t.itty = "b" WHERE ... 

및 코드, 어떤 복사 units 테이블 field1field2에서 값을 같이 될 것입니다 : 키워드는, 같은 WHERE 당신은 a를 SET를 사용하여 쿼리 및 을 생성 할 수 있습니다

relation = Unit.all um = Arel::UpdateManager.new(relation.engine) um.table(relation.table) um.ast.wheres = relation.wheres.to_a um.set(Arel::Nodes::SqlLiteral.new('field1 = "field2"')) ActiveRecord::Base.connection.execute(um.to_sql) 

정확하게 추가 방법을 사용하여 관계를 업데이트 할 수 있습니다. 따라서 우리는 Arel의 UpdateManager을 만들고 테이블에 where 절을 지정하고 설정할 값을 지정합니다. 값 쉘은 메소드에 인수로 전달됩니다. 생성 된 SQL 요청에 FROM 키워드를 추가해야합니다. UPDATE 절 자체로 지정된 외부 테이블에 액세스 할 수있는 경우에만 추가합니다. 마지막으로 쿼리를 실행합니다. 그래서 우리가 얻을 :

def update_relation!(relation, values) 
    um = Arel::UpdateManager.new(relation.engine) 
    um.table(relation.table) 
    um.ast.wheres = relation.wheres.to_a 
    um.set(values) 
    sql = um.to_sql 

    # appends FROM field to the query if needed 
    m = sql.match(/WHERE/) 
    tables = relation.arel.source.to_a.select {|v| v.class == Arel::Table }.map(&:name).uniq 
    tables.shift 
    sql.insert(m.begin(0), "FROM #{tables.join(",")} ") if m && !tables.empty? 

    # executes the query 
    ActiveRecord::Base.connection.execute(sql) 
end 

당신은 관계 업데이트를 실행할 수 있습니다으로 :

values = Arel::Nodes::SqlLiteral.new('field1 = "field2", field2 = NULL') 
relation = Unit.not_rejected.where(Unit.arel_table[:field2].not_eq(nil)) 
update_relation!(relation, values)