Gem source code Demo source code
Author: Bogdan Gusiev

User Grid (basic) Time Entry Grid (advanced)

Time Entries Grid


Developer Project Report hours
Claudette Hagenes repudiandae officiis qui 147.0
Ethyl Ankunding animi aperiam tenetur 121.0
Ethyl Ankunding eum amet quia 120.0
Tami Gibson doloribus hic corporis 115.0
Alise Rolfson animi aperiam tenetur 115.0
Beverlee Auer eum amet quia 112.0
Alex Legros odio velit repudiandae 110.0
Tamera Bogan odio velit repudiandae 110.0
Eleonore Wisozk doloribus hic corporis 110.0
Adrienne Eichmann repudiandae officiis qui 110.0
Milagros Lemke odio velit repudiandae 110.0
Micheal Jenkins repudiandae officiis qui 108.0
Penney Schowalter animi aperiam tenetur 107.0
Myrtle O'Conner repudiandae officiis qui 107.0
Elida Zulauf perspiciatis totam perferendis 107.0
Gwendolyn Satterfield suscipit consectetur beatae 105.0
Brigid McLaughlin saepe hic temporibus 105.0
Carlota Gottlieb odio velit repudiandae 105.0
Juliana Hauck odio velit repudiandae 104.0
Bong Witting eum amet quia 104.0
Palmira Fay vitae eum pariatur 104.0
Bong Witting doloribus hic corporis 103.0
Juliana Hauck repudiandae officiis qui 103.0
Lesia Hyatt repudiandae officiis qui 102.0
Vivien Murray quibusdam sed sit 102.0

Grid:

class TimeEntriesGrid < BaseGrid

  #
  # Scope
  #

  scope do
    User.select(
      "users.name, projects.name as project_name, accounts.name as account_name, sum(time_entries.hours) as report_hours"
    ).joins(:time_entries => {:project => :account}).group("projects.name", "users.name", "accounts.name").order("users.name")

  end


  #
  # Filters
  #

  filter(:project_id, :enum,
    :select => lambda {Project.all.map {|p| [p.name, p.id]}},
    :multiple => true,
    :include_blank => false
  ) do |value|
    self.where(:time_entries => {:project_id => value})
  end


  filter(:year, :enum,
         :select => lambda { TimeEntry.all.any? ? (TimeEntry.minimum(:date).year..TimeEntry.maximum(:date).year) : []},
    :include_blank => false,
    :default => lambda {Date.today.year}
  ) do |value|
    self.where(["extract(year from time_entries.date) = ?", value.to_i])
  end

  filter(:month, :enum,
         :select => Date::MONTHNAMES[1..12].enum_for(:each_with_index).collect {|name, index| [name, index + 1]},
         :include_blank => false,
         :default => lambda {Date.today.month}
        ) do |value|

    self.where(["extract(month from time_entries.date) = ?", value.to_i])
  end


  #
  # Columns
  #

  column(:user_name, :header => "Developer", :order => "users.name") do
    self.name
  end
  column(:project_name, :header => "Project", :order => "projects.name")
  column(
    :account_name,
    :header => "Company",
    :order => "accounts.name",
  ) do |model|
    format(model.account_name) do
      render :partial => "time_entries/company", :locals => {:model => model}
    end
  end

  column(:report_hours, order: "sum(time_entries.hours)")

end

Controller:

class TimeEntriesController < ApplicationController

  def index
    @time_entries_grid = TimeEntriesGrid.new(params[:g]) do |scope|
      scope.page(params[:page] )
    end
  end
end

View:


<h3>Time Entries Grid</h3>


<div class="left">
  <%= datagrid_form_for @time_entries_grid, url: time_entries_path %>
  <br/>

  <%= datagrid_table(@time_entries_grid) %>
  <%= paginate @time_entries_grid.assets %>

</div>

<div class="right">
  <%= render :partial => "shared/source", :object => @time_entries_grid %>
</div>