议程日程/名册视图

时间:2015-12-13 08:41:17

标签: ruby-on-rails ruby postgresql

我想显示一个议程,显示接下来七天有谁可以获得名册,具有以下逻辑:

每天7天中的每一天循环:

  1. 如果今天开始休假,请显示Starts %H:%M
  2. 如果请假今天结束,请显示Finishes %H:%M
  3. 如果请假开始并在今天结束,请显示%H:%M - %H:%M
  4. 如果今天的假期没有开始或结束,但今天仍然有效,请显示all day
  5. 应包括在7天之外开始或结束但在展示的7天内休假。
  6. 我希望有人能指出我正确的方向,最好使用Rails和Postgres。我并不反对每天进行查询,因为最多只会显示30天,但也会寻找合理的性能代码,因为每天可能有100多条休假记录。

    第一个不符合上述标准的例子。

    <% @dates.each do |d| %>
      <h5><%= d.strftime("%A %d %b") %></h5>
      <% @leave = Leave.where('(start_at BETWEEN ? AND ?) OR (end_at BETWEEN ? AND ?)', d.beginning_of_day, d.end_of_day, d.beginning_of_day, d.end_of_day) %>
      <% @leave = @leave.where.not('end_at < ?', Time.current) %>
    
      <% if @leave.any? %>
        <ul>
          <% @leave.each do |leave| %>
            <% if leave.single_day? && leave.start_at.to_date == d %>
              <li>
                <label class="label label-danger"><%= leave.start_at.strftime('%H:%M') %> - <%= leave.end_at.strftime('%H:%M') %></label>
                <%= leave.user.name %>
              </li>
            <% elsif !leave.single_day? %>
              <% if leave.start_at.to_date == d %>
                <li>
                  <label class="label label-danger">From <%= leave.start_at.strftime('%H:%M') %></label>
                  <%= leave.user.name %>
                </li>
              <% elsif leave.end_at.to_date == d %>
                <li>
                  <label class="label label-danger">Until <%= leave.end_at.strftime('%H:%M') %></label>
                  <%= leave.user.name %>
                </li>
              <% else %>
                <li>
                  <label class="label label-danger">All Day</label>
                  <%= leave.user.name %>
                </li>
              <% end %>
            <% end %>
          <% end %>
        </ul>
        <br/>
        <span class="label label-success" style="margin-right: 10px;">
          <span class="glyphicon glyphicon-ok"></span>
        </span>
        <%= current_account.users.active.where.not(id: @leave.map(&:user_id)).count %> Available
      <% else %>
        <span class="label label-success" style="margin-right: 10px;">
          <span class="glyphicon glyphicon-ok"></span>
        </span>
        <%= current_account.users.active.count %> Available
      <% end %>
    
      <br />
      <br />
    <% end %>
    

2 个答案:

答案 0 :(得分:1)

我会从这样的事情开始:

在模型中:

def starts_on?(date)
  start_at.to_date == date
end

def ends_on?(date)
  end_at.to_date = date
end

def covers?(date)
  leave.start_at.to_date <= date && leave.end_at.to_date >= date
end

def starts_and_ends_on?(date)
  starts_on?(date) && ends_on?(date)
end

在控制器中:

@dates = # define the date range like you already do, I assume it is an array
@leaves = Leave.includes(:user).
                where('start_at =< ? AND end_at >= ?', dates.max, dates.min)

在帮手中:

def relevant_leaves_for_date(date, leaves)
  leaves.select { |leave| leave.covers?(date) }
end

def leave_description_for_date(leave, date)
  if leave.starts_and_ends_on?(date)
    "#{leave.start_at.strftime('%H:%M')} - #{leave.end_at.strftime('%H:%M')}"
  elsif leave.starts_on?(date)
    "From #{leave.start_at.strftime('%H:%M')}"
  elsif leave.ends_on?(date)
    "Until #{leave.end_at.strftime('%H:%M')}"
  else
    'All day'
  end
end

def available_users(leaves)
  current_account.users.active.count - leaves.size
end

在视图中:

<% @dates.each do |date| %>
  <h5><%= date.strftime("%A %d %b") %></h5>

  <% leaves = relevant_leaves_for_date(date, @leaves) %>
  <% if leaves.any? %>
    <ul>

      <% leaves.each do |leave| %>
        <li>
          <label class="label label-danger">
            <%= leave_description_for_date(leave, date) %>
          </label>
          <%= leave.user.name %>
        </li>
      <% end %>

    </ul>
  <% end %>

  <span class="label label-success">
    <span class="glyphicon glyphicon-ok"></span>
  </span>
  <%= available_users(leaves) %> Available
<% end %>

您可能会注意到我从html中删除了<br>style标记。请不要在html中使用<br>作为样式或style属性。添加类标记并在css文件中设置样式。

答案 1 :(得分:0)

案例4&amp;如果您没有取出在一天开始之前开始或将在一天结束之后结束的树叶,则5不起作用。所以你可以获取尚未结束的所有叶子。

<% @leave = Leave.where('(end_at >= ?', d.beginning_of_day) %>

然后在 application_helper.rb 中,您可以拥有这样的功能,

def check_for_leave(leave,d)
 msg = ""
 if leave.single_day? && leave.start_at.to_date == d 
  msg = "#{leave.start_at.strftime('%H:%M')}  - #{leave.end_at.strftime('%H:%M')}"
 elsif !leave.single_day? 
  if leave.start_at.to_date == d 
   msg = "From #{leave.start_at.strftime('%H:%M')}" 
  elsif leave.end_at.to_date == d
   msg = "Until #{leave.end_at.strftime('%H:%M')}" 
  else
   msg = "All Day"    
  end
 return msg
end

html.erb 文件

<% @dates.each do |d| %>
  <h5><%= d.strftime("%A %d %b") %></h5>
  <% @leave = Leave.where('(end_at >= ?', d.beginning_of_day) %>
  <% if @leave.any? %>
    <ul>
      <% @leave.each do |leave| %>
        <li>
            <label class="label label-danger">
                <%= check_for_leave(leave, d) %>
            </label>    
            <%= leave.user.name %>
        </li>
      <% end %>
    </ul>
    <br/>
    <span class="label label-success" style="margin-right: 10px;">
      <span class="glyphicon glyphicon-ok"></span>
    </span>
    <%= current_account.users.active.where.not(id: @leave.map(&:user_id)).count %> Available
  <% else %>
    <span class="label label-success" style="margin-right: 10px;">
      <span class="glyphicon glyphicon-ok"></span>
    </span>
    <%= current_account.users.active.count %> Available
  <% end %>

  <br />
  <br />
<% end %>