You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ruby on Rails:使用Ransack实现按周日期范围筛选列表

实现按日期复选框筛选整周活动列表

看起来你已经搭好了Ransack搜索的基础框架,接下来我们一步步把按日期复选框筛选整周活动的功能补全:

1. 完善控制器逻辑(events_controller.rb)

我们需要在index方法里处理复选框提交的日期参数,把选中的日期转换成对应周的日期范围,再传给Ransack做筛选:

# events_controller.rb
def index
  @q = Event.ransack(params[:q])
  
  # 处理选中的周日期筛选逻辑
  if params[:selected_weeks].present?
    # 将选中的日期字符串转为Date对象,再计算对应周的起止日期
    week_ranges = params[:selected_weeks].map do |date_str|
      target_date = Date.parse(date_str)
      # 按照学期设置的周起始日(比如周一/周日)计算整周范围
      week_start = target_date - target_date.wday + Semester.current.start_dt.wday
      week_end = week_start + 6
      week_start..week_end
    end
    # 筛选活动日期落在任意选中周范围内的记录
    @q = Event.ransack(event_date_in: week_ranges.flatten)
  end

  @events = @q.result(distinct: true) # 加上distinct避免重复数据
  
  # 生成可选的周起始日期列表(保留你原来的逻辑)
  @weeks = Semester.current.range.select {|w| w.wday == Semester.current.start_dt.wday}.map(&:to_s)
end

2. 完善视图的复选框表单(index.html.erb)

在搜索表单里添加日期复选框组,确保选中的日期能正确传递给控制器:

<div class="col-10">
  <div class="dates">
    <%= search_form_for @q, id: "filters_click", remote: true do |f| %>
      <!-- 周日期复选框组 -->
      <div class="week-checkboxes d-flex flex-wrap gap-3">
        <% @weeks.each do |week_date| %>
          <div class="form-check">
            <%= check_box_tag 'selected_weeks[]', week_date, params[:selected_weeks]&.include?(week_date), class: 'form-check-input' %>
            <%= label_tag "selected_weeks_#{week_date}", "周起始:#{week_date}", class: 'form-check-label' %>
          </div>
        <% end %>
      </div>

      <!-- 可选:添加提交按钮,或者设置点击复选框自动提交 -->
      <%= f.submit '筛选', class: 'btn btn-primary mt-3' %>
    <% end %>
  </div>

  <!-- 活动列表展示区 -->
  <div class="events-list mt-4">
    <% @events.each do |event| %>
      <div class="card mb-2">
        <div class="card-body">
          <h5 class="card-title"><%= event.title %></h5>
          <p class="card-text">日期:<%= event.event_date.strftime('%Y-%m-%d') %></p>
          <!-- 其他活动信息按需添加 -->
        </div>
      </div>
    <% end %>
  </div>
</div>

3. 复选框点击自动提交(可选优化)

如果不想每次选完都点提交按钮,可以加一段JS实现点击复选框自动提交表单:

// 可以放在index.html.erb末尾,或者单独的JS文件中
document.addEventListener('DOMContentLoaded', function() {
  const checkboxes = document.querySelectorAll('.week-checkboxes .form-check-input');
  const filterForm = document.getElementById('filters_click');

  checkboxes.forEach(box => {
    box.addEventListener('change', () => filterForm.submit());
  });
});

关键细节说明

  • 用selected_weeks[]作为复选框的name,这样多个选中的日期会以数组形式提交到控制器
  • 控制器里把每个选中日期转换成对应周的起止范围,再用Ransack的event_date_in条件筛选匹配的活动
  • 确保Semester.current.range返回的是有效的日期数组,这样@weeks才能正确生成周起始日期选项

内容的提问来源于stack exchange,提问作者degenPenguin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:25:35