Mercurial > hg > soundsoftware-site
comparison app/controllers/timelog_controller.rb @ 1298:4f746d8966dd redmine_2.3_integration
Merge from redmine-2.3 branch to create new branch redmine-2.3-integration
author | Chris Cannam |
---|---|
date | Fri, 14 Jun 2013 09:28:30 +0100 |
parents | 622f24f53b42 |
children |
comparison
equal
deleted
inserted
replaced
1297:0a574315af3e | 1298:4f746d8966dd |
---|---|
1 # Redmine - project management software | 1 # Redmine - project management software |
2 # Copyright (C) 2006-2012 Jean-Philippe Lang | 2 # Copyright (C) 2006-2013 Jean-Philippe Lang |
3 # | 3 # |
4 # This program is free software; you can redistribute it and/or | 4 # This program is free software; you can redistribute it and/or |
5 # modify it under the terms of the GNU General Public License | 5 # modify it under the terms of the GNU General Public License |
6 # as published by the Free Software Foundation; either version 2 | 6 # as published by the Free Software Foundation; either version 2 |
7 # of the License, or (at your option) any later version. | 7 # of the License, or (at your option) any later version. |
28 before_filter :authorize_global, :only => [:new, :index, :report] | 28 before_filter :authorize_global, :only => [:new, :index, :report] |
29 | 29 |
30 accept_rss_auth :index | 30 accept_rss_auth :index |
31 accept_api_auth :index, :show, :create, :update, :destroy | 31 accept_api_auth :index, :show, :create, :update, :destroy |
32 | 32 |
33 rescue_from Query::StatementInvalid, :with => :query_statement_invalid | |
34 | |
33 helper :sort | 35 helper :sort |
34 include SortHelper | 36 include SortHelper |
35 helper :issues | 37 helper :issues |
36 include TimelogHelper | 38 include TimelogHelper |
37 helper :custom_fields | 39 helper :custom_fields |
38 include CustomFieldsHelper | 40 include CustomFieldsHelper |
41 helper :queries | |
42 include QueriesHelper | |
39 | 43 |
40 def index | 44 def index |
41 sort_init 'spent_on', 'desc' | 45 @query = TimeEntryQuery.build_from_params(params, :project => @project, :name => '_') |
42 sort_update 'spent_on' => ['spent_on', "#{TimeEntry.table_name}.created_on"], | 46 scope = time_entry_scope |
43 'user' => 'user_id', | 47 |
44 'activity' => 'activity_id', | 48 sort_init(@query.sort_criteria.empty? ? [['spent_on', 'desc']] : @query.sort_criteria) |
45 'project' => "#{Project.table_name}.name", | 49 sort_update(@query.sortable_columns) |
46 'issue' => 'issue_id', | |
47 'hours' => 'hours' | |
48 | |
49 retrieve_date_range | |
50 | |
51 scope = TimeEntry.visible.spent_between(@from, @to) | |
52 if @issue | |
53 scope = scope.on_issue(@issue) | |
54 elsif @project | |
55 scope = scope.on_project(@project, Setting.display_subprojects_issues?) | |
56 end | |
57 | 50 |
58 respond_to do |format| | 51 respond_to do |format| |
59 format.html { | 52 format.html { |
60 # Paginate results | 53 # Paginate results |
61 @entry_count = scope.count | 54 @entry_count = scope.count |
62 @entry_pages = Paginator.new self, @entry_count, per_page_option, params['page'] | 55 @entry_pages = Paginator.new @entry_count, per_page_option, params['page'] |
63 @entries = scope.all( | 56 @entries = scope.all( |
64 :include => [:project, :activity, :user, {:issue => :tracker}], | 57 :include => [:project, :activity, :user, {:issue => :tracker}], |
65 :order => sort_clause, | 58 :order => sort_clause, |
66 :limit => @entry_pages.items_per_page, | 59 :limit => @entry_pages.per_page, |
67 :offset => @entry_pages.current.offset | 60 :offset => @entry_pages.offset |
68 ) | 61 ) |
69 @total_hours = scope.sum(:hours).to_f | 62 @total_hours = scope.sum(:hours).to_f |
70 | 63 |
71 render :layout => !request.xhr? | 64 render :layout => !request.xhr? |
72 } | 65 } |
92 # Export all entries | 85 # Export all entries |
93 @entries = scope.all( | 86 @entries = scope.all( |
94 :include => [:project, :activity, :user, {:issue => [:tracker, :assigned_to, :priority]}], | 87 :include => [:project, :activity, :user, {:issue => [:tracker, :assigned_to, :priority]}], |
95 :order => sort_clause | 88 :order => sort_clause |
96 ) | 89 ) |
97 send_data(entries_to_csv(@entries), :type => 'text/csv; header=present', :filename => 'timelog.csv') | 90 send_data(query_to_csv(@entries, @query, params), :type => 'text/csv; header=present', :filename => 'timelog.csv') |
98 } | 91 } |
99 end | 92 end |
100 end | 93 end |
101 | 94 |
102 def report | 95 def report |
103 retrieve_date_range | 96 @query = TimeEntryQuery.build_from_params(params, :project => @project, :name => '_') |
104 @report = Redmine::Helpers::TimeReport.new(@project, @issue, params[:criteria], params[:columns], @from, @to) | 97 scope = time_entry_scope |
98 | |
99 @report = Redmine::Helpers::TimeReport.new(@project, @issue, params[:criteria], params[:columns], scope) | |
105 | 100 |
106 respond_to do |format| | 101 respond_to do |format| |
107 format.html { render :layout => !request.xhr? } | 102 format.html { render :layout => !request.xhr? } |
108 format.csv { send_data(report_to_csv(@report), :type => 'text/csv; header=present', :filename => 'timelog.csv') } | 103 format.csv { send_data(report_to_csv(@report), :type => 'text/csv; header=present', :filename => 'timelog.csv') } |
109 end | 104 end |
132 respond_to do |format| | 127 respond_to do |format| |
133 format.html { | 128 format.html { |
134 flash[:notice] = l(:notice_successful_create) | 129 flash[:notice] = l(:notice_successful_create) |
135 if params[:continue] | 130 if params[:continue] |
136 if params[:project_id] | 131 if params[:project_id] |
137 redirect_to :action => 'new', :project_id => @time_entry.project, :issue_id => @time_entry.issue, | 132 options = { |
138 :time_entry => {:issue_id => @time_entry.issue_id, :activity_id => @time_entry.activity_id}, | 133 :time_entry => {:issue_id => @time_entry.issue_id, :activity_id => @time_entry.activity_id}, |
139 :back_url => params[:back_url] | 134 :back_url => params[:back_url] |
135 } | |
136 if @time_entry.issue | |
137 redirect_to new_project_issue_time_entry_path(@time_entry.project, @time_entry.issue, options) | |
138 else | |
139 redirect_to new_project_time_entry_path(@time_entry.project, options) | |
140 end | |
140 else | 141 else |
141 redirect_to :action => 'new', | 142 options = { |
142 :time_entry => {:project_id => @time_entry.project_id, :issue_id => @time_entry.issue_id, :activity_id => @time_entry.activity_id}, | 143 :time_entry => {:project_id => @time_entry.project_id, :issue_id => @time_entry.issue_id, :activity_id => @time_entry.activity_id}, |
143 :back_url => params[:back_url] | 144 :back_url => params[:back_url] |
145 } | |
146 redirect_to new_time_entry_path(options) | |
144 end | 147 end |
145 else | 148 else |
146 redirect_back_or_default :action => 'index', :project_id => @time_entry.project | 149 redirect_back_or_default project_time_entries_path(@time_entry.project) |
147 end | 150 end |
148 } | 151 } |
149 format.api { render :action => 'show', :status => :created, :location => time_entry_url(@time_entry) } | 152 format.api { render :action => 'show', :status => :created, :location => time_entry_url(@time_entry) } |
150 end | 153 end |
151 else | 154 else |
167 | 170 |
168 if @time_entry.save | 171 if @time_entry.save |
169 respond_to do |format| | 172 respond_to do |format| |
170 format.html { | 173 format.html { |
171 flash[:notice] = l(:notice_successful_update) | 174 flash[:notice] = l(:notice_successful_update) |
172 redirect_back_or_default :action => 'index', :project_id => @time_entry.project | 175 redirect_back_or_default project_time_entries_path(@time_entry.project) |
173 } | 176 } |
174 format.api { render_api_ok } | 177 format.api { render_api_ok } |
175 end | 178 end |
176 else | 179 else |
177 respond_to do |format| | 180 respond_to do |format| |
198 # Keep unsaved time_entry ids to display them in flash error | 201 # Keep unsaved time_entry ids to display them in flash error |
199 unsaved_time_entry_ids << time_entry.id | 202 unsaved_time_entry_ids << time_entry.id |
200 end | 203 end |
201 end | 204 end |
202 set_flash_from_bulk_time_entry_save(@time_entries, unsaved_time_entry_ids) | 205 set_flash_from_bulk_time_entry_save(@time_entries, unsaved_time_entry_ids) |
203 redirect_back_or_default({:controller => 'timelog', :action => 'index', :project_id => @projects.first}) | 206 redirect_back_or_default project_time_entries_path(@projects.first) |
204 end | 207 end |
205 | 208 |
206 def destroy | 209 def destroy |
207 destroyed = TimeEntry.transaction do | 210 destroyed = TimeEntry.transaction do |
208 @time_entries.each do |t| | 211 @time_entries.each do |t| |
217 if destroyed | 220 if destroyed |
218 flash[:notice] = l(:notice_successful_delete) | 221 flash[:notice] = l(:notice_successful_delete) |
219 else | 222 else |
220 flash[:error] = l(:notice_unable_delete_time_entry) | 223 flash[:error] = l(:notice_unable_delete_time_entry) |
221 end | 224 end |
222 redirect_back_or_default(:action => 'index', :project_id => @projects.first) | 225 redirect_back_or_default project_time_entries_path(@projects.first) |
223 } | 226 } |
224 format.api { | 227 format.api { |
225 if destroyed | 228 if destroyed |
226 render_api_ok | 229 render_api_ok |
227 else | 230 else |
289 elsif !params[:project_id].blank? | 292 elsif !params[:project_id].blank? |
290 @project = Project.find(params[:project_id]) | 293 @project = Project.find(params[:project_id]) |
291 end | 294 end |
292 end | 295 end |
293 | 296 |
294 # Retrieves the date range based on predefined ranges or specific from/to param dates | 297 # Returns the TimeEntry scope for index and report actions |
295 def retrieve_date_range | 298 def time_entry_scope |
296 @free_period = false | 299 scope = TimeEntry.visible.where(@query.statement) |
297 @from, @to = nil, nil | 300 if @issue |
298 | 301 scope = scope.on_issue(@issue) |
299 if params[:period_type] == '1' || (params[:period_type].nil? && !params[:period].nil?) | 302 elsif @project |
300 case params[:period].to_s | 303 scope = scope.on_project(@project, Setting.display_subprojects_issues?) |
301 when 'today' | 304 end |
302 @from = @to = Date.today | 305 scope |
303 when 'yesterday' | |
304 @from = @to = Date.today - 1 | |
305 when 'current_week' | |
306 @from = Date.today - (Date.today.cwday - 1)%7 | |
307 @to = @from + 6 | |
308 when 'last_week' | |
309 @from = Date.today - 7 - (Date.today.cwday - 1)%7 | |
310 @to = @from + 6 | |
311 when 'last_2_weeks' | |
312 @from = Date.today - 14 - (Date.today.cwday - 1)%7 | |
313 @to = @from + 13 | |
314 when '7_days' | |
315 @from = Date.today - 7 | |
316 @to = Date.today | |
317 when 'current_month' | |
318 @from = Date.civil(Date.today.year, Date.today.month, 1) | |
319 @to = (@from >> 1) - 1 | |
320 when 'last_month' | |
321 @from = Date.civil(Date.today.year, Date.today.month, 1) << 1 | |
322 @to = (@from >> 1) - 1 | |
323 when '30_days' | |
324 @from = Date.today - 30 | |
325 @to = Date.today | |
326 when 'current_year' | |
327 @from = Date.civil(Date.today.year, 1, 1) | |
328 @to = Date.civil(Date.today.year, 12, 31) | |
329 end | |
330 elsif params[:period_type] == '2' || (params[:period_type].nil? && (!params[:from].nil? || !params[:to].nil?)) | |
331 begin; @from = params[:from].to_s.to_date unless params[:from].blank?; rescue; end | |
332 begin; @to = params[:to].to_s.to_date unless params[:to].blank?; rescue; end | |
333 @free_period = true | |
334 else | |
335 # default | |
336 end | |
337 | |
338 @from, @to = @to, @from if @from && @to && @from > @to | |
339 end | 306 end |
340 | 307 |
341 def parse_params_for_bulk_time_entry_attributes(params) | 308 def parse_params_for_bulk_time_entry_attributes(params) |
342 attributes = (params[:time_entry] || {}).reject {|k,v| v.blank?} | 309 attributes = (params[:time_entry] || {}).reject {|k,v| v.blank?} |
343 attributes.keys.each {|k| attributes[k] = '' if attributes[k] == 'none'} | 310 attributes.keys.each {|k| attributes[k] = '' if attributes[k] == 'none'} |