Enums를 사용하는 속성에 따라 Active Admin에서 확인란 필터 만들기
12766 단어 Railsactiveadmin
결론
Active Admin에서 Active Record를 사용하는 EnumsActiveRecord::Enum
의 모델의 속성을 사용하는 필터를 콤보 상자 형식으로 만들려면 Enums의 키-value 매핑을 건네주는Hash.# app/models/user.rb
class User
enum status: { active: 0, suspended: 1, inactive: 2 }
end
# app/admin/user.rb
ActiveAdmin.register User do
filter :status, as: :check_boxes, collection: User.statuses
# User.statuses #=> { active: 0, suspended: 1, inactive: 2 }
end
active
/suspended
에서 검색
다음은 순조롭지 못한 상황에 대해 설명한다.
불순한 상황
키 목록만 전달User.statuses.keys
하면 키 목록만 전달할 때 생성된 폼으로 서버에 제출하면 서버 측이 Ransack을 통해 검색할 때 순조롭게 진행되지 않습니다.# app/admin/user.rb
ActiveAdmin.register User do
filter :status, as: :check_boxes, collection: User.statuses.keys
# User.statuses.keys #=> ["active", "suspended", "inactive"]
end
suspended
에서 검색된 레코드만 표시active
무슨 문제 있어요?
생성된 창 구조
check_boxes
Enums 키 목록만 Filter에 전달하면 생성된 폼의 input 탭value
은 상태 문자열을 유지합니다.<div class="check_boxes input optional filter_form_field filter_check_boxes" id="q_status_input">
<fieldset class="choices">
<legend class="label">
<label>Status</label>
</legend>
<label for="q_status_preparing">
<input type="checkbox" name="q[status_in][]" id="q_status_preparing" value="preparing"> preparing
</label>
<label for="q_status_transferring">
<input type="checkbox" name="q[status_in][]" id="q_status_transferring" value="transferring">transferring
</label>
<label for="q_status_succeeded">
<input type="checkbox" name="q[status_in][]" id="q_status_succeeded" value="succeeded">succeeded
</label>
<label for="q_status_failed"><input type="checkbox" name="q[status_in][]" id="q_status_failed" value="failed"> failed
</label>
</fieldset>
</div>
input 탭의 value
는 status
키입니다.커밋하면 서버측 Ransack이 이 값에 따라 레코드를 찾습니다.이때 Enums의 속성은 원래 수치로 검색되었지만 문자열을 교부하면 Enums의 최초 요소의 값(지금은 0)이 사용되었다.이 로그는 다음과 같습니다.Started GET "/admin/users?q%5Bstatus_in%5D%5B%5D=active&q%5Bstatus_in%5D%5B%5D=suspended&commit=Filter&order=id_desc" for ::1 at 2019-11-22 10:24:30 +0900
Processing by Admin::UsersController#index as HTML
Parameters: {"q"=>{"status_in"=>["active", "suspended"]}, "commit"=>"Filter", "order"=>"id_desc"}
Rendering /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb
(0.2ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
(0.1ms) SELECT COUNT(*) FROM "users" WHERE "users"."status" IN (0, 0)
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
User Load (0.2ms) SELECT "users".* FROM "users" WHERE "users"."status" IN (0, 0) ORDER BY "users"."id" desc LIMIT ? OFFSET ? [["LIMIT", 30], ["OFFSET", 0]]
Rendered /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb (Duration: 145.3ms | Allocations: 117153)
Completed 200 OK in 147ms (Views: 145.2ms | ActiveRecord: 0.6ms | Allocations: 118179)
이렇게 하면 어떤 체크 상자로 필터를 하든지 최초의 요소만 검색합니다.
정답인 경우 다음 테이블이 생성됩니다.<div class="check_boxes input optional filter_form_field filter_check_boxes" id="q_status_input">
<fieldset class="choices">
<legend class="label">
<label>Status</label>
</legend>
<label for="q_status_0">
<input type="checkbox" name="q[status_in][]" id="q_status_0" value="0"> preparing
</label>
<label for="q_status_1">
<input type="checkbox" name="q[status_in][]" id="q_status_1" value="1"> transferring
</label>
<label for="q_status_2">
<input type="checkbox" name="q[status_in][]" id="q_status_2" value="2"> succeeded
</label>
<label for="q_status_3">
<input type="checkbox" name="q[status_in][]" id="q_status_3" value="3"> failed
</label>
</fieldset>
</div>
input 탭의 value
는 정수값입니다. 이 옵션을 제출하면 정확하게 검색할 수 있습니다.이 로그는 다음과 같습니다.Started GET "/admin/users?q%5Bstatus_in%5D%5B%5D=0&q%5Bstatus_in%5D%5B%5D=1&commit=Filter&order=id_desc" for ::1 at 2019-11-22 10:22:18 +0900
Processing by Admin::UsersController#index as HTML
Parameters: {"q"=>{"status_in"=>["0", "1"]}, "commit"=>"Filter", "order"=>"id_desc"}
Rendering /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb
(0.2ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
(0.1ms) SELECT COUNT(*) FROM "users" WHERE "users"."status" IN (0, 1)
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
User Load (0.1ms) SELECT "users".* FROM "users" WHERE "users"."status" IN (0, 1) ORDER BY "users"."id" desc LIMIT ? OFFSET ? [["LIMIT", 30], ["OFFSET", 0]]
Rendered /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb (Duration: 142.3ms | Allocations: 117716)
Completed 200 OK in 144ms (Views: 142.2ms | ActiveRecord: 0.5ms | Allocations: 118736)
참고 자료
# app/models/user.rb
class User
enum status: { active: 0, suspended: 1, inactive: 2 }
end
# app/admin/user.rb
ActiveAdmin.register User do
filter :status, as: :check_boxes, collection: User.statuses
# User.statuses #=> { active: 0, suspended: 1, inactive: 2 }
end
키 목록만 전달
User.statuses.keys
하면 키 목록만 전달할 때 생성된 폼으로 서버에 제출하면 서버 측이 Ransack을 통해 검색할 때 순조롭게 진행되지 않습니다.# app/admin/user.rb
ActiveAdmin.register User do
filter :status, as: :check_boxes, collection: User.statuses.keys
# User.statuses.keys #=> ["active", "suspended", "inactive"]
end
suspended
에서 검색된 레코드만 표시active
무슨 문제 있어요?
생성된 창 구조
check_boxes
Enums 키 목록만 Filter에 전달하면 생성된 폼의 input 탭value
은 상태 문자열을 유지합니다.<div class="check_boxes input optional filter_form_field filter_check_boxes" id="q_status_input">
<fieldset class="choices">
<legend class="label">
<label>Status</label>
</legend>
<label for="q_status_preparing">
<input type="checkbox" name="q[status_in][]" id="q_status_preparing" value="preparing"> preparing
</label>
<label for="q_status_transferring">
<input type="checkbox" name="q[status_in][]" id="q_status_transferring" value="transferring">transferring
</label>
<label for="q_status_succeeded">
<input type="checkbox" name="q[status_in][]" id="q_status_succeeded" value="succeeded">succeeded
</label>
<label for="q_status_failed"><input type="checkbox" name="q[status_in][]" id="q_status_failed" value="failed"> failed
</label>
</fieldset>
</div>
input 탭의 value
는 status
키입니다.커밋하면 서버측 Ransack이 이 값에 따라 레코드를 찾습니다.이때 Enums의 속성은 원래 수치로 검색되었지만 문자열을 교부하면 Enums의 최초 요소의 값(지금은 0)이 사용되었다.이 로그는 다음과 같습니다.Started GET "/admin/users?q%5Bstatus_in%5D%5B%5D=active&q%5Bstatus_in%5D%5B%5D=suspended&commit=Filter&order=id_desc" for ::1 at 2019-11-22 10:24:30 +0900
Processing by Admin::UsersController#index as HTML
Parameters: {"q"=>{"status_in"=>["active", "suspended"]}, "commit"=>"Filter", "order"=>"id_desc"}
Rendering /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb
(0.2ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
(0.1ms) SELECT COUNT(*) FROM "users" WHERE "users"."status" IN (0, 0)
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 0) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
User Load (0.2ms) SELECT "users".* FROM "users" WHERE "users"."status" IN (0, 0) ORDER BY "users"."id" desc LIMIT ? OFFSET ? [["LIMIT", 30], ["OFFSET", 0]]
Rendered /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb (Duration: 145.3ms | Allocations: 117153)
Completed 200 OK in 147ms (Views: 145.2ms | ActiveRecord: 0.6ms | Allocations: 118179)
이렇게 하면 어떤 체크 상자로 필터를 하든지 최초의 요소만 검색합니다.정답인 경우 다음 테이블이 생성됩니다.
<div class="check_boxes input optional filter_form_field filter_check_boxes" id="q_status_input">
<fieldset class="choices">
<legend class="label">
<label>Status</label>
</legend>
<label for="q_status_0">
<input type="checkbox" name="q[status_in][]" id="q_status_0" value="0"> preparing
</label>
<label for="q_status_1">
<input type="checkbox" name="q[status_in][]" id="q_status_1" value="1"> transferring
</label>
<label for="q_status_2">
<input type="checkbox" name="q[status_in][]" id="q_status_2" value="2"> succeeded
</label>
<label for="q_status_3">
<input type="checkbox" name="q[status_in][]" id="q_status_3" value="3"> failed
</label>
</fieldset>
</div>
input 탭의 value
는 정수값입니다. 이 옵션을 제출하면 정확하게 검색할 수 있습니다.이 로그는 다음과 같습니다.Started GET "/admin/users?q%5Bstatus_in%5D%5B%5D=0&q%5Bstatus_in%5D%5B%5D=1&commit=Filter&order=id_desc" for ::1 at 2019-11-22 10:22:18 +0900
Processing by Admin::UsersController#index as HTML
Parameters: {"q"=>{"status_in"=>["0", "1"]}, "commit"=>"Filter", "order"=>"id_desc"}
Rendering /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb
(0.2ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
(0.1ms) SELECT COUNT(*) FROM "users" WHERE "users"."status" IN (0, 1)
CACHE (0.0ms) SELECT COUNT(*) FROM (SELECT 1 AS one FROM "users" WHERE "users"."status" IN (0, 1) LIMIT ? OFFSET ?) subquery_for_count [["LIMIT", 30], ["OFFSET", 0]]
User Load (0.1ms) SELECT "users".* FROM "users" WHERE "users"."status" IN (0, 1) ORDER BY "users"."id" desc LIMIT ? OFFSET ? [["LIMIT", 30], ["OFFSET", 0]]
Rendered /Users/kymmt90/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activeadmin-2.4.0/app/views/active_admin/resource/index.html.arb (Duration: 142.3ms | Allocations: 117716)
Completed 200 OK in 144ms (Views: 142.2ms | ActiveRecord: 0.5ms | Allocations: 118736)
참고 자료
Reference
이 문제에 관하여(Enums를 사용하는 속성에 따라 Active Admin에서 확인란 필터 만들기), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/kymmt90/items/42b3763e8882eabb5a15텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)