##// END OF EJS Templates
Adds a test for when query is not found....
Jean-Philippe Lang -
r9039:67e8d1113ef0
parent child
Show More
@@ -1,3105 +1,3110
1 1 # Redmine - project management software
2 2 # Copyright (C) 2006-2012 Jean-Philippe Lang
3 3 #
4 4 # This program is free software; you can redistribute it and/or
5 5 # modify it under the terms of the GNU General Public License
6 6 # as published by the Free Software Foundation; either version 2
7 7 # of the License, or (at your option) any later version.
8 8 #
9 9 # This program is distributed in the hope that it will be useful,
10 10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 12 # GNU General Public License for more details.
13 13 #
14 14 # You should have received a copy of the GNU General Public License
15 15 # along with this program; if not, write to the Free Software
16 16 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17 17
18 18 require File.expand_path('../../test_helper', __FILE__)
19 19 require 'issues_controller'
20 20
21 21 class IssuesControllerTest < ActionController::TestCase
22 22 fixtures :projects,
23 23 :users,
24 24 :roles,
25 25 :members,
26 26 :member_roles,
27 27 :issues,
28 28 :issue_statuses,
29 29 :versions,
30 30 :trackers,
31 31 :projects_trackers,
32 32 :issue_categories,
33 33 :enabled_modules,
34 34 :enumerations,
35 35 :attachments,
36 36 :workflows,
37 37 :custom_fields,
38 38 :custom_values,
39 39 :custom_fields_projects,
40 40 :custom_fields_trackers,
41 41 :time_entries,
42 42 :journals,
43 43 :journal_details,
44 44 :queries,
45 45 :repositories,
46 46 :changesets
47 47
48 48 include Redmine::I18n
49 49
50 50 def setup
51 51 @controller = IssuesController.new
52 52 @request = ActionController::TestRequest.new
53 53 @response = ActionController::TestResponse.new
54 54 User.current = nil
55 55 end
56 56
57 57 def test_index
58 58 with_settings :default_language => "en" do
59 59 get :index
60 60 assert_response :success
61 61 assert_template 'index'
62 62 assert_not_nil assigns(:issues)
63 63 assert_nil assigns(:project)
64 64 assert_tag :tag => 'a', :content => /Can't print recipes/
65 65 assert_tag :tag => 'a', :content => /Subproject issue/
66 66 # private projects hidden
67 67 assert_no_tag :tag => 'a', :content => /Issue of a private subproject/
68 68 assert_no_tag :tag => 'a', :content => /Issue on project 2/
69 69 # project column
70 70 assert_tag :tag => 'th', :content => /Project/
71 71 end
72 72 end
73 73
74 74 def test_index_should_not_list_issues_when_module_disabled
75 75 EnabledModule.delete_all("name = 'issue_tracking' AND project_id = 1")
76 76 get :index
77 77 assert_response :success
78 78 assert_template 'index'
79 79 assert_not_nil assigns(:issues)
80 80 assert_nil assigns(:project)
81 81 assert_no_tag :tag => 'a', :content => /Can't print recipes/
82 82 assert_tag :tag => 'a', :content => /Subproject issue/
83 83 end
84 84
85 85 def test_index_should_list_visible_issues_only
86 86 get :index, :per_page => 100
87 87 assert_response :success
88 88 assert_not_nil assigns(:issues)
89 89 assert_nil assigns(:issues).detect {|issue| !issue.visible?}
90 90 end
91 91
92 92 def test_index_with_project
93 93 Setting.display_subprojects_issues = 0
94 94 get :index, :project_id => 1
95 95 assert_response :success
96 96 assert_template 'index'
97 97 assert_not_nil assigns(:issues)
98 98 assert_tag :tag => 'a', :content => /Can't print recipes/
99 99 assert_no_tag :tag => 'a', :content => /Subproject issue/
100 100 end
101 101
102 102 def test_index_with_project_and_subprojects
103 103 Setting.display_subprojects_issues = 1
104 104 get :index, :project_id => 1
105 105 assert_response :success
106 106 assert_template 'index'
107 107 assert_not_nil assigns(:issues)
108 108 assert_tag :tag => 'a', :content => /Can't print recipes/
109 109 assert_tag :tag => 'a', :content => /Subproject issue/
110 110 assert_no_tag :tag => 'a', :content => /Issue of a private subproject/
111 111 end
112 112
113 113 def test_index_with_project_and_subprojects_should_show_private_subprojects
114 114 @request.session[:user_id] = 2
115 115 Setting.display_subprojects_issues = 1
116 116 get :index, :project_id => 1
117 117 assert_response :success
118 118 assert_template 'index'
119 119 assert_not_nil assigns(:issues)
120 120 assert_tag :tag => 'a', :content => /Can't print recipes/
121 121 assert_tag :tag => 'a', :content => /Subproject issue/
122 122 assert_tag :tag => 'a', :content => /Issue of a private subproject/
123 123 end
124 124
125 125 def test_index_with_project_and_default_filter
126 126 get :index, :project_id => 1, :set_filter => 1
127 127 assert_response :success
128 128 assert_template 'index'
129 129 assert_not_nil assigns(:issues)
130 130
131 131 query = assigns(:query)
132 132 assert_not_nil query
133 133 # default filter
134 134 assert_equal({'status_id' => {:operator => 'o', :values => ['']}}, query.filters)
135 135 end
136 136
137 137 def test_index_with_project_and_filter
138 138 get :index, :project_id => 1, :set_filter => 1,
139 139 :f => ['tracker_id'],
140 140 :op => {'tracker_id' => '='},
141 141 :v => {'tracker_id' => ['1']}
142 142 assert_response :success
143 143 assert_template 'index'
144 144 assert_not_nil assigns(:issues)
145 145
146 146 query = assigns(:query)
147 147 assert_not_nil query
148 148 assert_equal({'tracker_id' => {:operator => '=', :values => ['1']}}, query.filters)
149 149 end
150 150
151 151 def test_index_with_short_filters
152 152 to_test = {
153 153 'status_id' => {
154 154 'o' => { :op => 'o', :values => [''] },
155 155 'c' => { :op => 'c', :values => [''] },
156 156 '7' => { :op => '=', :values => ['7'] },
157 157 '7|3|4' => { :op => '=', :values => ['7', '3', '4'] },
158 158 '=7' => { :op => '=', :values => ['7'] },
159 159 '!3' => { :op => '!', :values => ['3'] },
160 160 '!7|3|4' => { :op => '!', :values => ['7', '3', '4'] }},
161 161 'subject' => {
162 162 'This is a subject' => { :op => '=', :values => ['This is a subject'] },
163 163 'o' => { :op => '=', :values => ['o'] },
164 164 '~This is part of a subject' => { :op => '~', :values => ['This is part of a subject'] },
165 165 '!~This is part of a subject' => { :op => '!~', :values => ['This is part of a subject'] }},
166 166 'tracker_id' => {
167 167 '3' => { :op => '=', :values => ['3'] },
168 168 '=3' => { :op => '=', :values => ['3'] }},
169 169 'start_date' => {
170 170 '2011-10-12' => { :op => '=', :values => ['2011-10-12'] },
171 171 '=2011-10-12' => { :op => '=', :values => ['2011-10-12'] },
172 172 '>=2011-10-12' => { :op => '>=', :values => ['2011-10-12'] },
173 173 '<=2011-10-12' => { :op => '<=', :values => ['2011-10-12'] },
174 174 '><2011-10-01|2011-10-30' => { :op => '><', :values => ['2011-10-01', '2011-10-30'] },
175 175 '<t+2' => { :op => '<t+', :values => ['2'] },
176 176 '>t+2' => { :op => '>t+', :values => ['2'] },
177 177 't+2' => { :op => 't+', :values => ['2'] },
178 178 't' => { :op => 't', :values => [''] },
179 179 'w' => { :op => 'w', :values => [''] },
180 180 '>t-2' => { :op => '>t-', :values => ['2'] },
181 181 '<t-2' => { :op => '<t-', :values => ['2'] },
182 182 't-2' => { :op => 't-', :values => ['2'] }},
183 183 'created_on' => {
184 184 '>=2011-10-12' => { :op => '>=', :values => ['2011-10-12'] },
185 185 '<t-2' => { :op => '<t-', :values => ['2'] },
186 186 '>t-2' => { :op => '>t-', :values => ['2'] },
187 187 't-2' => { :op => 't-', :values => ['2'] }},
188 188 'cf_1' => {
189 189 'c' => { :op => '=', :values => ['c'] },
190 190 '!c' => { :op => '!', :values => ['c'] },
191 191 '!*' => { :op => '!*', :values => [''] },
192 192 '*' => { :op => '*', :values => [''] }},
193 193 'estimated_hours' => {
194 194 '=13.4' => { :op => '=', :values => ['13.4'] },
195 195 '>=45' => { :op => '>=', :values => ['45'] },
196 196 '<=125' => { :op => '<=', :values => ['125'] },
197 197 '><10.5|20.5' => { :op => '><', :values => ['10.5', '20.5'] },
198 198 '!*' => { :op => '!*', :values => [''] },
199 199 '*' => { :op => '*', :values => [''] }}
200 200 }
201 201
202 202 default_filter = { 'status_id' => {:operator => 'o', :values => [''] }}
203 203
204 204 to_test.each do |field, expression_and_expected|
205 205 expression_and_expected.each do |filter_expression, expected|
206 206
207 207 get :index, :set_filter => 1, field => filter_expression
208 208
209 209 assert_response :success
210 210 assert_template 'index'
211 211 assert_not_nil assigns(:issues)
212 212
213 213 query = assigns(:query)
214 214 assert_not_nil query
215 215 assert query.has_filter?(field)
216 216 assert_equal(default_filter.merge({field => {:operator => expected[:op], :values => expected[:values]}}), query.filters)
217 217 end
218 218 end
219 219 end
220 220
221 221 def test_index_with_project_and_empty_filters
222 222 get :index, :project_id => 1, :set_filter => 1, :fields => ['']
223 223 assert_response :success
224 224 assert_template 'index'
225 225 assert_not_nil assigns(:issues)
226 226
227 227 query = assigns(:query)
228 228 assert_not_nil query
229 229 # no filter
230 230 assert_equal({}, query.filters)
231 231 end
232 232
233 233 def test_index_with_query
234 234 get :index, :project_id => 1, :query_id => 5
235 235 assert_response :success
236 236 assert_template 'index'
237 237 assert_not_nil assigns(:issues)
238 238 assert_nil assigns(:issue_count_by_group)
239 239 end
240 240
241 241 def test_index_with_query_grouped_by_tracker
242 242 get :index, :project_id => 1, :query_id => 6
243 243 assert_response :success
244 244 assert_template 'index'
245 245 assert_not_nil assigns(:issues)
246 246 assert_not_nil assigns(:issue_count_by_group)
247 247 end
248 248
249 249 def test_index_with_query_grouped_by_list_custom_field
250 250 get :index, :project_id => 1, :query_id => 9
251 251 assert_response :success
252 252 assert_template 'index'
253 253 assert_not_nil assigns(:issues)
254 254 assert_not_nil assigns(:issue_count_by_group)
255 255 end
256 256
257 257 def test_index_with_query_id_and_project_id_should_set_session_query
258 258 get :index, :project_id => 1, :query_id => 4
259 259 assert_response :success
260 260 assert_kind_of Hash, session[:query]
261 261 assert_equal 4, session[:query][:id]
262 262 assert_equal 1, session[:query][:project_id]
263 263 end
264 264
265 def test_index_with_invalid_query_id_should_respond_404
266 get :index, :project_id => 1, :query_id => 999
267 assert_response 404
268 end
269
265 270 def test_index_with_cross_project_query_in_session_should_show_project_issues
266 271 q = Query.create!(:name => "test", :user_id => 2, :is_public => false, :project => nil)
267 272 @request.session[:query] = {:id => q.id, :project_id => 1}
268 273
269 274 with_settings :display_subprojects_issues => '0' do
270 275 get :index, :project_id => 1
271 276 end
272 277 assert_response :success
273 278 assert_not_nil assigns(:query)
274 279 assert_equal q.id, assigns(:query).id
275 280 assert_equal 1, assigns(:query).project_id
276 281 assert_equal [1], assigns(:issues).map(&:project_id).uniq
277 282 end
278 283
279 284 def test_private_query_should_not_be_available_to_other_users
280 285 q = Query.create!(:name => "private", :user => User.find(2), :is_public => false, :project => nil)
281 286 @request.session[:user_id] = 3
282 287
283 288 get :index, :query_id => q.id
284 289 assert_response 403
285 290 end
286 291
287 292 def test_private_query_should_be_available_to_its_user
288 293 q = Query.create!(:name => "private", :user => User.find(2), :is_public => false, :project => nil)
289 294 @request.session[:user_id] = 2
290 295
291 296 get :index, :query_id => q.id
292 297 assert_response :success
293 298 end
294 299
295 300 def test_public_query_should_be_available_to_other_users
296 301 q = Query.create!(:name => "private", :user => User.find(2), :is_public => true, :project => nil)
297 302 @request.session[:user_id] = 3
298 303
299 304 get :index, :query_id => q.id
300 305 assert_response :success
301 306 end
302 307
303 308 def test_index_csv
304 309 get :index, :format => 'csv'
305 310 assert_response :success
306 311 assert_not_nil assigns(:issues)
307 312 assert_equal 'text/csv', @response.content_type
308 313 assert @response.body.starts_with?("#,")
309 314 lines = @response.body.chomp.split("\n")
310 315 assert_equal assigns(:query).columns.size + 1, lines[0].split(',').size
311 316 end
312 317
313 318 def test_index_csv_with_project
314 319 get :index, :project_id => 1, :format => 'csv'
315 320 assert_response :success
316 321 assert_not_nil assigns(:issues)
317 322 assert_equal 'text/csv', @response.content_type
318 323 end
319 324
320 325 def test_index_csv_with_description
321 326 get :index, :format => 'csv', :description => '1'
322 327 assert_response :success
323 328 assert_not_nil assigns(:issues)
324 329 assert_equal 'text/csv', @response.content_type
325 330 assert @response.body.starts_with?("#,")
326 331 lines = @response.body.chomp.split("\n")
327 332 assert_equal assigns(:query).columns.size + 2, lines[0].split(',').size
328 333 end
329 334
330 335 def test_index_csv_with_spent_time_column
331 336 issue = Issue.create!(:project_id => 1, :tracker_id => 1, :subject => 'test_index_csv_with_spent_time_column', :author_id => 2)
332 337 TimeEntry.create!(:project => issue.project, :issue => issue, :hours => 7.33, :user => User.find(2), :spent_on => Date.today)
333 338
334 339 get :index, :format => 'csv', :set_filter => '1', :c => %w(subject spent_hours)
335 340 assert_response :success
336 341 assert_equal 'text/csv', @response.content_type
337 342 lines = @response.body.chomp.split("\n")
338 343 assert_include "#{issue.id},#{issue.subject},7.33", lines
339 344 end
340 345
341 346 def test_index_csv_with_all_columns
342 347 get :index, :format => 'csv', :columns => 'all'
343 348 assert_response :success
344 349 assert_not_nil assigns(:issues)
345 350 assert_equal 'text/csv', @response.content_type
346 351 assert @response.body.starts_with?("#,")
347 352 lines = @response.body.chomp.split("\n")
348 353 assert_equal assigns(:query).available_columns.size + 1, lines[0].split(',').size
349 354 end
350 355
351 356 def test_index_csv_with_multi_column_field
352 357 CustomField.find(1).update_attribute :multiple, true
353 358 issue = Issue.find(1)
354 359 issue.custom_field_values = {1 => ['MySQL', 'Oracle']}
355 360 issue.save!
356 361
357 362 get :index, :format => 'csv', :columns => 'all'
358 363 assert_response :success
359 364 lines = @response.body.chomp.split("\n")
360 365 assert lines.detect {|line| line.include?('"MySQL, Oracle"')}
361 366 end
362 367
363 368 def test_index_csv_big_5
364 369 with_settings :default_language => "zh-TW" do
365 370 str_utf8 = "\xe4\xb8\x80\xe6\x9c\x88"
366 371 str_big5 = "\xa4@\xa4\xeb"
367 372 if str_utf8.respond_to?(:force_encoding)
368 373 str_utf8.force_encoding('UTF-8')
369 374 str_big5.force_encoding('Big5')
370 375 end
371 376 issue = Issue.new(:project_id => 1, :tracker_id => 1, :author_id => 3,
372 377 :status_id => 1, :priority => IssuePriority.all.first,
373 378 :subject => str_utf8)
374 379 assert issue.save
375 380
376 381 get :index, :project_id => 1,
377 382 :f => ['subject'],
378 383 :op => '=', :values => [str_utf8],
379 384 :format => 'csv'
380 385 assert_equal 'text/csv', @response.content_type
381 386 lines = @response.body.chomp.split("\n")
382 387 s1 = "\xaa\xac\xbaA"
383 388 if str_utf8.respond_to?(:force_encoding)
384 389 s1.force_encoding('Big5')
385 390 end
386 391 assert lines[0].include?(s1)
387 392 assert lines[1].include?(str_big5)
388 393 end
389 394 end
390 395
391 396 def test_index_csv_cannot_convert_should_be_replaced_big_5
392 397 with_settings :default_language => "zh-TW" do
393 398 str_utf8 = "\xe4\xbb\xa5\xe5\x86\x85"
394 399 if str_utf8.respond_to?(:force_encoding)
395 400 str_utf8.force_encoding('UTF-8')
396 401 end
397 402 issue = Issue.new(:project_id => 1, :tracker_id => 1, :author_id => 3,
398 403 :status_id => 1, :priority => IssuePriority.all.first,
399 404 :subject => str_utf8)
400 405 assert issue.save
401 406
402 407 get :index, :project_id => 1,
403 408 :f => ['subject'],
404 409 :op => '=', :values => [str_utf8],
405 410 :c => ['status', 'subject'],
406 411 :format => 'csv',
407 412 :set_filter => 1
408 413 assert_equal 'text/csv', @response.content_type
409 414 lines = @response.body.chomp.split("\n")
410 415 s1 = "\xaa\xac\xbaA" # status
411 416 if str_utf8.respond_to?(:force_encoding)
412 417 s1.force_encoding('Big5')
413 418 end
414 419 assert lines[0].include?(s1)
415 420 s2 = lines[1].split(",")[2]
416 421 if s1.respond_to?(:force_encoding)
417 422 s3 = "\xa5H?" # subject
418 423 s3.force_encoding('Big5')
419 424 assert_equal s3, s2
420 425 elsif RUBY_PLATFORM == 'java'
421 426 assert_equal "??", s2
422 427 else
423 428 assert_equal "\xa5H???", s2
424 429 end
425 430 end
426 431 end
427 432
428 433 def test_index_csv_tw
429 434 with_settings :default_language => "zh-TW" do
430 435 str1 = "test_index_csv_tw"
431 436 issue = Issue.new(:project_id => 1, :tracker_id => 1, :author_id => 3,
432 437 :status_id => 1, :priority => IssuePriority.all.first,
433 438 :subject => str1, :estimated_hours => '1234.5')
434 439 assert issue.save
435 440 assert_equal 1234.5, issue.estimated_hours
436 441
437 442 get :index, :project_id => 1,
438 443 :f => ['subject'],
439 444 :op => '=', :values => [str1],
440 445 :c => ['estimated_hours', 'subject'],
441 446 :format => 'csv',
442 447 :set_filter => 1
443 448 assert_equal 'text/csv', @response.content_type
444 449 lines = @response.body.chomp.split("\n")
445 450 assert_equal "#{issue.id},1234.50,#{str1}", lines[1]
446 451
447 452 str_tw = "Traditional Chinese (\xe7\xb9\x81\xe9\xab\x94\xe4\xb8\xad\xe6\x96\x87)"
448 453 if str_tw.respond_to?(:force_encoding)
449 454 str_tw.force_encoding('UTF-8')
450 455 end
451 456 assert_equal str_tw, l(:general_lang_name)
452 457 assert_equal ',', l(:general_csv_separator)
453 458 assert_equal '.', l(:general_csv_decimal_separator)
454 459 end
455 460 end
456 461
457 462 def test_index_csv_fr
458 463 with_settings :default_language => "fr" do
459 464 str1 = "test_index_csv_fr"
460 465 issue = Issue.new(:project_id => 1, :tracker_id => 1, :author_id => 3,
461 466 :status_id => 1, :priority => IssuePriority.all.first,
462 467 :subject => str1, :estimated_hours => '1234.5')
463 468 assert issue.save
464 469 assert_equal 1234.5, issue.estimated_hours
465 470
466 471 get :index, :project_id => 1,
467 472 :f => ['subject'],
468 473 :op => '=', :values => [str1],
469 474 :c => ['estimated_hours', 'subject'],
470 475 :format => 'csv',
471 476 :set_filter => 1
472 477 assert_equal 'text/csv', @response.content_type
473 478 lines = @response.body.chomp.split("\n")
474 479 assert_equal "#{issue.id};1234,50;#{str1}", lines[1]
475 480
476 481 str_fr = "Fran\xc3\xa7ais"
477 482 if str_fr.respond_to?(:force_encoding)
478 483 str_fr.force_encoding('UTF-8')
479 484 end
480 485 assert_equal str_fr, l(:general_lang_name)
481 486 assert_equal ';', l(:general_csv_separator)
482 487 assert_equal ',', l(:general_csv_decimal_separator)
483 488 end
484 489 end
485 490
486 491 def test_index_pdf
487 492 ["en", "zh", "zh-TW", "ja", "ko"].each do |lang|
488 493 with_settings :default_language => lang do
489 494
490 495 get :index
491 496 assert_response :success
492 497 assert_template 'index'
493 498
494 499 if lang == "ja"
495 500 if RUBY_PLATFORM != 'java'
496 501 assert_equal "CP932", l(:general_pdf_encoding)
497 502 end
498 503 if RUBY_PLATFORM == 'java' && l(:general_pdf_encoding) == "CP932"
499 504 next
500 505 end
501 506 end
502 507
503 508 get :index, :format => 'pdf'
504 509 assert_response :success
505 510 assert_not_nil assigns(:issues)
506 511 assert_equal 'application/pdf', @response.content_type
507 512
508 513 get :index, :project_id => 1, :format => 'pdf'
509 514 assert_response :success
510 515 assert_not_nil assigns(:issues)
511 516 assert_equal 'application/pdf', @response.content_type
512 517
513 518 get :index, :project_id => 1, :query_id => 6, :format => 'pdf'
514 519 assert_response :success
515 520 assert_not_nil assigns(:issues)
516 521 assert_equal 'application/pdf', @response.content_type
517 522 end
518 523 end
519 524 end
520 525
521 526 def test_index_pdf_with_query_grouped_by_list_custom_field
522 527 get :index, :project_id => 1, :query_id => 9, :format => 'pdf'
523 528 assert_response :success
524 529 assert_not_nil assigns(:issues)
525 530 assert_not_nil assigns(:issue_count_by_group)
526 531 assert_equal 'application/pdf', @response.content_type
527 532 end
528 533
529 534 def test_index_sort
530 535 get :index, :sort => 'tracker,id:desc'
531 536 assert_response :success
532 537
533 538 sort_params = @request.session['issues_index_sort']
534 539 assert sort_params.is_a?(String)
535 540 assert_equal 'tracker,id:desc', sort_params
536 541
537 542 issues = assigns(:issues)
538 543 assert_not_nil issues
539 544 assert !issues.empty?
540 545 assert_equal issues.sort {|a,b| a.tracker == b.tracker ? b.id <=> a.id : a.tracker <=> b.tracker }.collect(&:id), issues.collect(&:id)
541 546 end
542 547
543 548 def test_index_sort_by_field_not_included_in_columns
544 549 Setting.issue_list_default_columns = %w(subject author)
545 550 get :index, :sort => 'tracker'
546 551 end
547 552
548 553 def test_index_sort_by_assigned_to
549 554 get :index, :sort => 'assigned_to'
550 555 assert_response :success
551 556 assignees = assigns(:issues).collect(&:assigned_to).compact
552 557 assert_equal assignees.sort, assignees
553 558 end
554 559
555 560 def test_index_sort_by_assigned_to_desc
556 561 get :index, :sort => 'assigned_to:desc'
557 562 assert_response :success
558 563 assignees = assigns(:issues).collect(&:assigned_to).compact
559 564 assert_equal assignees.sort.reverse, assignees
560 565 end
561 566
562 567 def test_index_group_by_assigned_to
563 568 get :index, :group_by => 'assigned_to', :sort => 'priority'
564 569 assert_response :success
565 570 end
566 571
567 572 def test_index_sort_by_author
568 573 get :index, :sort => 'author'
569 574 assert_response :success
570 575 authors = assigns(:issues).collect(&:author)
571 576 assert_equal authors.sort, authors
572 577 end
573 578
574 579 def test_index_sort_by_author_desc
575 580 get :index, :sort => 'author:desc'
576 581 assert_response :success
577 582 authors = assigns(:issues).collect(&:author)
578 583 assert_equal authors.sort.reverse, authors
579 584 end
580 585
581 586 def test_index_group_by_author
582 587 get :index, :group_by => 'author', :sort => 'priority'
583 588 assert_response :success
584 589 end
585 590
586 591 def test_index_sort_by_spent_hours
587 592 get :index, :sort => 'spent_hours:desc'
588 593 assert_response :success
589 594 hours = assigns(:issues).collect(&:spent_hours)
590 595 assert_equal hours.sort.reverse, hours
591 596 end
592 597
593 598 def test_index_with_columns
594 599 columns = ['tracker', 'subject', 'assigned_to']
595 600 get :index, :set_filter => 1, :c => columns
596 601 assert_response :success
597 602
598 603 # query should use specified columns
599 604 query = assigns(:query)
600 605 assert_kind_of Query, query
601 606 assert_equal columns, query.column_names.map(&:to_s)
602 607
603 608 # columns should be stored in session
604 609 assert_kind_of Hash, session[:query]
605 610 assert_kind_of Array, session[:query][:column_names]
606 611 assert_equal columns, session[:query][:column_names].map(&:to_s)
607 612
608 613 # ensure only these columns are kept in the selected columns list
609 614 assert_tag :tag => 'select', :attributes => { :id => 'selected_columns' },
610 615 :children => { :count => 3 }
611 616 assert_no_tag :tag => 'option', :attributes => { :value => 'project' },
612 617 :parent => { :tag => 'select', :attributes => { :id => "selected_columns" } }
613 618 end
614 619
615 620 def test_index_without_project_should_implicitly_add_project_column_to_default_columns
616 621 Setting.issue_list_default_columns = ['tracker', 'subject', 'assigned_to']
617 622 get :index, :set_filter => 1
618 623
619 624 # query should use specified columns
620 625 query = assigns(:query)
621 626 assert_kind_of Query, query
622 627 assert_equal [:project, :tracker, :subject, :assigned_to], query.columns.map(&:name)
623 628 end
624 629
625 630 def test_index_without_project_and_explicit_default_columns_should_not_add_project_column
626 631 Setting.issue_list_default_columns = ['tracker', 'subject', 'assigned_to']
627 632 columns = ['tracker', 'subject', 'assigned_to']
628 633 get :index, :set_filter => 1, :c => columns
629 634
630 635 # query should use specified columns
631 636 query = assigns(:query)
632 637 assert_kind_of Query, query
633 638 assert_equal columns.map(&:to_sym), query.columns.map(&:name)
634 639 end
635 640
636 641 def test_index_with_custom_field_column
637 642 columns = %w(tracker subject cf_2)
638 643 get :index, :set_filter => 1, :c => columns
639 644 assert_response :success
640 645
641 646 # query should use specified columns
642 647 query = assigns(:query)
643 648 assert_kind_of Query, query
644 649 assert_equal columns, query.column_names.map(&:to_s)
645 650
646 651 assert_tag :td,
647 652 :attributes => {:class => 'cf_2 string'},
648 653 :ancestor => {:tag => 'table', :attributes => {:class => /issues/}}
649 654 end
650 655
651 656 def test_index_with_multi_custom_field_column
652 657 field = CustomField.find(1)
653 658 field.update_attribute :multiple, true
654 659 issue = Issue.find(1)
655 660 issue.custom_field_values = {1 => ['MySQL', 'Oracle']}
656 661 issue.save!
657 662
658 663 get :index, :set_filter => 1, :c => %w(tracker subject cf_1)
659 664 assert_response :success
660 665
661 666 assert_tag :td,
662 667 :attributes => {:class => /cf_1/},
663 668 :content => 'MySQL, Oracle'
664 669 end
665 670
666 671 def test_index_with_multi_user_custom_field_column
667 672 field = IssueCustomField.create!(:name => 'Multi user', :field_format => 'user', :multiple => true,
668 673 :tracker_ids => [1], :is_for_all => true)
669 674 issue = Issue.find(1)
670 675 issue.custom_field_values = {field.id => ['2', '3']}
671 676 issue.save!
672 677
673 678 get :index, :set_filter => 1, :c => ['tracker', 'subject', "cf_#{field.id}"]
674 679 assert_response :success
675 680
676 681 assert_tag :td,
677 682 :attributes => {:class => /cf_#{field.id}/},
678 683 :child => {:tag => 'a', :content => 'John Smith'}
679 684 end
680 685
681 686 def test_index_with_date_column
682 687 Issue.find(1).update_attribute :start_date, '1987-08-24'
683 688
684 689 with_settings :date_format => '%d/%m/%Y' do
685 690 get :index, :set_filter => 1, :c => %w(start_date)
686 691 assert_tag 'td', :attributes => {:class => /start_date/}, :content => '24/08/1987'
687 692 end
688 693 end
689 694
690 695 def test_index_with_done_ratio
691 696 Issue.find(1).update_attribute :done_ratio, 40
692 697
693 698 get :index, :set_filter => 1, :c => %w(done_ratio)
694 699 assert_tag 'td', :attributes => {:class => /done_ratio/},
695 700 :child => {:tag => 'table', :attributes => {:class => 'progress'},
696 701 :descendant => {:tag => 'td', :attributes => {:class => 'closed', :style => 'width: 40%;'}}
697 702 }
698 703 end
699 704
700 705 def test_index_with_spent_hours_column
701 706 get :index, :set_filter => 1, :c => %w(subject spent_hours)
702 707
703 708 assert_tag 'tr', :attributes => {:id => 'issue-3'},
704 709 :child => {
705 710 :tag => 'td', :attributes => {:class => /spent_hours/}, :content => '1.00'
706 711 }
707 712 end
708 713
709 714 def test_index_should_not_show_spent_hours_column_without_permission
710 715 Role.anonymous.remove_permission! :view_time_entries
711 716 get :index, :set_filter => 1, :c => %w(subject spent_hours)
712 717
713 718 assert_no_tag 'td', :attributes => {:class => /spent_hours/}
714 719 end
715 720
716 721 def test_index_with_fixed_version
717 722 get :index, :set_filter => 1, :c => %w(fixed_version)
718 723 assert_tag 'td', :attributes => {:class => /fixed_version/},
719 724 :child => {:tag => 'a', :content => '1.0', :attributes => {:href => '/versions/2'}}
720 725 end
721 726
722 727 def test_index_send_html_if_query_is_invalid
723 728 get :index, :f => ['start_date'], :op => {:start_date => '='}
724 729 assert_equal 'text/html', @response.content_type
725 730 assert_template 'index'
726 731 end
727 732
728 733 def test_index_send_nothing_if_query_is_invalid
729 734 get :index, :f => ['start_date'], :op => {:start_date => '='}, :format => 'csv'
730 735 assert_equal 'text/csv', @response.content_type
731 736 assert @response.body.blank?
732 737 end
733 738
734 739 def test_show_by_anonymous
735 740 get :show, :id => 1
736 741 assert_response :success
737 742 assert_template 'show'
738 743 assert_not_nil assigns(:issue)
739 744 assert_equal Issue.find(1), assigns(:issue)
740 745
741 746 # anonymous role is allowed to add a note
742 747 assert_tag :tag => 'form',
743 748 :descendant => { :tag => 'fieldset',
744 749 :child => { :tag => 'legend',
745 750 :content => /Notes/ } }
746 751 assert_tag :tag => 'title',
747 752 :content => "Bug #1: Can't print recipes - eCookbook - Redmine"
748 753 end
749 754
750 755 def test_show_by_manager
751 756 @request.session[:user_id] = 2
752 757 get :show, :id => 1
753 758 assert_response :success
754 759
755 760 assert_tag :tag => 'a',
756 761 :content => /Quote/
757 762
758 763 assert_tag :tag => 'form',
759 764 :descendant => { :tag => 'fieldset',
760 765 :child => { :tag => 'legend',
761 766 :content => /Change properties/ } },
762 767 :descendant => { :tag => 'fieldset',
763 768 :child => { :tag => 'legend',
764 769 :content => /Log time/ } },
765 770 :descendant => { :tag => 'fieldset',
766 771 :child => { :tag => 'legend',
767 772 :content => /Notes/ } }
768 773 end
769 774
770 775 def test_show_should_display_update_form
771 776 @request.session[:user_id] = 2
772 777 get :show, :id => 1
773 778 assert_response :success
774 779
775 780 assert_tag 'form', :attributes => {:id => 'issue-form'}
776 781 assert_tag 'input', :attributes => {:name => 'issue[is_private]'}
777 782 assert_tag 'select', :attributes => {:name => 'issue[project_id]'}
778 783 assert_tag 'select', :attributes => {:name => 'issue[tracker_id]'}
779 784 assert_tag 'input', :attributes => {:name => 'issue[subject]'}
780 785 assert_tag 'textarea', :attributes => {:name => 'issue[description]'}
781 786 assert_tag 'select', :attributes => {:name => 'issue[status_id]'}
782 787 assert_tag 'select', :attributes => {:name => 'issue[priority_id]'}
783 788 assert_tag 'select', :attributes => {:name => 'issue[assigned_to_id]'}
784 789 assert_tag 'select', :attributes => {:name => 'issue[category_id]'}
785 790 assert_tag 'select', :attributes => {:name => 'issue[fixed_version_id]'}
786 791 assert_tag 'input', :attributes => {:name => 'issue[parent_issue_id]'}
787 792 assert_tag 'input', :attributes => {:name => 'issue[start_date]'}
788 793 assert_tag 'input', :attributes => {:name => 'issue[due_date]'}
789 794 assert_tag 'select', :attributes => {:name => 'issue[done_ratio]'}
790 795 assert_tag 'input', :attributes => { :name => 'issue[custom_field_values][2]' }
791 796 assert_no_tag 'input', :attributes => {:name => 'issue[watcher_user_ids][]'}
792 797 assert_tag 'textarea', :attributes => {:name => 'notes'}
793 798 end
794 799
795 800 def test_show_should_display_update_form_with_minimal_permissions
796 801 Role.find(1).update_attribute :permissions, [:view_issues, :add_issue_notes]
797 802 Workflow.delete_all :role_id => 1
798 803
799 804 @request.session[:user_id] = 2
800 805 get :show, :id => 1
801 806 assert_response :success
802 807
803 808 assert_tag 'form', :attributes => {:id => 'issue-form'}
804 809 assert_no_tag 'input', :attributes => {:name => 'issue[is_private]'}
805 810 assert_no_tag 'select', :attributes => {:name => 'issue[project_id]'}
806 811 assert_no_tag 'select', :attributes => {:name => 'issue[tracker_id]'}
807 812 assert_no_tag 'input', :attributes => {:name => 'issue[subject]'}
808 813 assert_no_tag 'textarea', :attributes => {:name => 'issue[description]'}
809 814 assert_no_tag 'select', :attributes => {:name => 'issue[status_id]'}
810 815 assert_no_tag 'select', :attributes => {:name => 'issue[priority_id]'}
811 816 assert_no_tag 'select', :attributes => {:name => 'issue[assigned_to_id]'}
812 817 assert_no_tag 'select', :attributes => {:name => 'issue[category_id]'}
813 818 assert_no_tag 'select', :attributes => {:name => 'issue[fixed_version_id]'}
814 819 assert_no_tag 'input', :attributes => {:name => 'issue[parent_issue_id]'}
815 820 assert_no_tag 'input', :attributes => {:name => 'issue[start_date]'}
816 821 assert_no_tag 'input', :attributes => {:name => 'issue[due_date]'}
817 822 assert_no_tag 'select', :attributes => {:name => 'issue[done_ratio]'}
818 823 assert_no_tag 'input', :attributes => { :name => 'issue[custom_field_values][2]' }
819 824 assert_no_tag 'input', :attributes => {:name => 'issue[watcher_user_ids][]'}
820 825 assert_tag 'textarea', :attributes => {:name => 'notes'}
821 826 end
822 827
823 828 def test_show_should_display_update_form_with_workflow_permissions
824 829 Role.find(1).update_attribute :permissions, [:view_issues, :add_issue_notes]
825 830
826 831 @request.session[:user_id] = 2
827 832 get :show, :id => 1
828 833 assert_response :success
829 834
830 835 assert_tag 'form', :attributes => {:id => 'issue-form'}
831 836 assert_no_tag 'input', :attributes => {:name => 'issue[is_private]'}
832 837 assert_no_tag 'select', :attributes => {:name => 'issue[project_id]'}
833 838 assert_no_tag 'select', :attributes => {:name => 'issue[tracker_id]'}
834 839 assert_no_tag 'input', :attributes => {:name => 'issue[subject]'}
835 840 assert_no_tag 'textarea', :attributes => {:name => 'issue[description]'}
836 841 assert_tag 'select', :attributes => {:name => 'issue[status_id]'}
837 842 assert_no_tag 'select', :attributes => {:name => 'issue[priority_id]'}
838 843 assert_tag 'select', :attributes => {:name => 'issue[assigned_to_id]'}
839 844 assert_no_tag 'select', :attributes => {:name => 'issue[category_id]'}
840 845 assert_tag 'select', :attributes => {:name => 'issue[fixed_version_id]'}
841 846 assert_no_tag 'input', :attributes => {:name => 'issue[parent_issue_id]'}
842 847 assert_no_tag 'input', :attributes => {:name => 'issue[start_date]'}
843 848 assert_no_tag 'input', :attributes => {:name => 'issue[due_date]'}
844 849 assert_tag 'select', :attributes => {:name => 'issue[done_ratio]'}
845 850 assert_no_tag 'input', :attributes => { :name => 'issue[custom_field_values][2]' }
846 851 assert_no_tag 'input', :attributes => {:name => 'issue[watcher_user_ids][]'}
847 852 assert_tag 'textarea', :attributes => {:name => 'notes'}
848 853 end
849 854
850 855 def test_show_should_not_display_update_form_without_permissions
851 856 Role.find(1).update_attribute :permissions, [:view_issues]
852 857
853 858 @request.session[:user_id] = 2
854 859 get :show, :id => 1
855 860 assert_response :success
856 861
857 862 assert_no_tag 'form', :attributes => {:id => 'issue-form'}
858 863 end
859 864
860 865 def test_update_form_should_not_display_inactive_enumerations
861 866 @request.session[:user_id] = 2
862 867 get :show, :id => 1
863 868 assert_response :success
864 869
865 870 assert ! IssuePriority.find(15).active?
866 871 assert_no_tag :option, :attributes => {:value => '15'},
867 872 :parent => {:tag => 'select', :attributes => {:id => 'issue_priority_id'} }
868 873 end
869 874
870 875 def test_update_form_should_allow_attachment_upload
871 876 @request.session[:user_id] = 2
872 877 get :show, :id => 1
873 878
874 879 assert_tag :tag => 'form',
875 880 :attributes => {:id => 'issue-form', :method => 'post', :enctype => 'multipart/form-data'},
876 881 :descendant => {
877 882 :tag => 'input',
878 883 :attributes => {:type => 'file', :name => 'attachments[1][file]'}
879 884 }
880 885 end
881 886
882 887 def test_show_should_deny_anonymous_access_without_permission
883 888 Role.anonymous.remove_permission!(:view_issues)
884 889 get :show, :id => 1
885 890 assert_response :redirect
886 891 end
887 892
888 893 def test_show_should_deny_anonymous_access_to_private_issue
889 894 Issue.update_all(["is_private = ?", true], "id = 1")
890 895 get :show, :id => 1
891 896 assert_response :redirect
892 897 end
893 898
894 899 def test_show_should_deny_non_member_access_without_permission
895 900 Role.non_member.remove_permission!(:view_issues)
896 901 @request.session[:user_id] = 9
897 902 get :show, :id => 1
898 903 assert_response 403
899 904 end
900 905
901 906 def test_show_should_deny_non_member_access_to_private_issue
902 907 Issue.update_all(["is_private = ?", true], "id = 1")
903 908 @request.session[:user_id] = 9
904 909 get :show, :id => 1
905 910 assert_response 403
906 911 end
907 912
908 913 def test_show_should_deny_member_access_without_permission
909 914 Role.find(1).remove_permission!(:view_issues)
910 915 @request.session[:user_id] = 2
911 916 get :show, :id => 1
912 917 assert_response 403
913 918 end
914 919
915 920 def test_show_should_deny_member_access_to_private_issue_without_permission
916 921 Issue.update_all(["is_private = ?", true], "id = 1")
917 922 @request.session[:user_id] = 3
918 923 get :show, :id => 1
919 924 assert_response 403
920 925 end
921 926
922 927 def test_show_should_allow_author_access_to_private_issue
923 928 Issue.update_all(["is_private = ?, author_id = 3", true], "id = 1")
924 929 @request.session[:user_id] = 3
925 930 get :show, :id => 1
926 931 assert_response :success
927 932 end
928 933
929 934 def test_show_should_allow_assignee_access_to_private_issue
930 935 Issue.update_all(["is_private = ?, assigned_to_id = 3", true], "id = 1")
931 936 @request.session[:user_id] = 3
932 937 get :show, :id => 1
933 938 assert_response :success
934 939 end
935 940
936 941 def test_show_should_allow_member_access_to_private_issue_with_permission
937 942 Issue.update_all(["is_private = ?", true], "id = 1")
938 943 User.find(3).roles_for_project(Project.find(1)).first.update_attribute :issues_visibility, 'all'
939 944 @request.session[:user_id] = 3
940 945 get :show, :id => 1
941 946 assert_response :success
942 947 end
943 948
944 949 def test_show_should_not_disclose_relations_to_invisible_issues
945 950 Setting.cross_project_issue_relations = '1'
946 951 IssueRelation.create!(:issue_from => Issue.find(1), :issue_to => Issue.find(2), :relation_type => 'relates')
947 952 # Relation to a private project issue
948 953 IssueRelation.create!(:issue_from => Issue.find(1), :issue_to => Issue.find(4), :relation_type => 'relates')
949 954
950 955 get :show, :id => 1
951 956 assert_response :success
952 957
953 958 assert_tag :div, :attributes => { :id => 'relations' },
954 959 :descendant => { :tag => 'a', :content => /#2$/ }
955 960 assert_no_tag :div, :attributes => { :id => 'relations' },
956 961 :descendant => { :tag => 'a', :content => /#4$/ }
957 962 end
958 963
959 964 def test_show_should_list_subtasks
960 965 Issue.create!(:project_id => 1, :author_id => 1, :tracker_id => 1, :parent_issue_id => 1, :subject => 'Child Issue')
961 966
962 967 get :show, :id => 1
963 968 assert_response :success
964 969 assert_tag 'div', :attributes => {:id => 'issue_tree'},
965 970 :descendant => {:tag => 'td', :content => /Child Issue/, :attributes => {:class => /subject/}}
966 971 end
967 972
968 973 def test_show_should_list_parents
969 974 issue = Issue.create!(:project_id => 1, :author_id => 1, :tracker_id => 1, :parent_issue_id => 1, :subject => 'Child Issue')
970 975
971 976 get :show, :id => issue.id
972 977 assert_response :success
973 978 assert_tag 'div', :attributes => {:class => 'subject'},
974 979 :descendant => {:tag => 'h3', :content => 'Child Issue'}
975 980 assert_tag 'div', :attributes => {:class => 'subject'},
976 981 :descendant => {:tag => 'a', :attributes => {:href => '/issues/1'}}
977 982 end
978 983
979 984 def test_show_should_not_display_prev_next_links_without_query_in_session
980 985 get :show, :id => 1
981 986 assert_response :success
982 987 assert_nil assigns(:prev_issue_id)
983 988 assert_nil assigns(:next_issue_id)
984 989
985 990 assert_no_tag 'div', :attributes => {:class => /next-prev-links/}
986 991 end
987 992
988 993 def test_show_should_display_prev_next_links_with_query_in_session
989 994 @request.session[:query] = {:filters => {'status_id' => {:values => [''], :operator => 'o'}}, :project_id => nil}
990 995 @request.session['issues_index_sort'] = 'id'
991 996
992 997 with_settings :display_subprojects_issues => '0' do
993 998 get :show, :id => 3
994 999 end
995 1000
996 1001 assert_response :success
997 1002 # Previous and next issues for all projects
998 1003 assert_equal 2, assigns(:prev_issue_id)
999 1004 assert_equal 5, assigns(:next_issue_id)
1000 1005
1001 1006 assert_tag 'div', :attributes => {:class => /next-prev-links/}
1002 1007 assert_tag 'a', :attributes => {:href => '/issues/2'}, :content => /Previous/
1003 1008 assert_tag 'a', :attributes => {:href => '/issues/5'}, :content => /Next/
1004 1009
1005 1010 count = Issue.open.visible.count
1006 1011 assert_tag 'span', :attributes => {:class => 'position'}, :content => "3 of #{count}"
1007 1012 end
1008 1013
1009 1014 def test_show_should_display_prev_next_links_with_saved_query_in_session
1010 1015 query = Query.create!(:name => 'test', :is_public => true, :user_id => 1,
1011 1016 :filters => {'status_id' => {:values => ['5'], :operator => '='}},
1012 1017 :sort_criteria => [['id', 'asc']])
1013 1018 @request.session[:query] = {:id => query.id, :project_id => nil}
1014 1019
1015 1020 get :show, :id => 11
1016 1021
1017 1022 assert_response :success
1018 1023 assert_equal query, assigns(:query)
1019 1024 # Previous and next issues for all projects
1020 1025 assert_equal 8, assigns(:prev_issue_id)
1021 1026 assert_equal 12, assigns(:next_issue_id)
1022 1027
1023 1028 assert_tag 'a', :attributes => {:href => '/issues/8'}, :content => /Previous/
1024 1029 assert_tag 'a', :attributes => {:href => '/issues/12'}, :content => /Next/
1025 1030 end
1026 1031
1027 1032 def test_show_should_display_prev_next_links_with_query_and_sort_on_association
1028 1033 @request.session[:query] = {:filters => {'status_id' => {:values => [''], :operator => 'o'}}, :project_id => nil}
1029 1034
1030 1035 %w(project tracker status priority author assigned_to category fixed_version).each do |assoc_sort|
1031 1036 @request.session['issues_index_sort'] = assoc_sort
1032 1037
1033 1038 get :show, :id => 3
1034 1039 assert_response :success, "Wrong response status for #{assoc_sort} sort"
1035 1040
1036 1041 assert_tag 'div', :attributes => {:class => /next-prev-links/}, :content => /Previous/
1037 1042 assert_tag 'div', :attributes => {:class => /next-prev-links/}, :content => /Next/
1038 1043 end
1039 1044 end
1040 1045
1041 1046 def test_show_should_display_prev_next_links_with_project_query_in_session
1042 1047 @request.session[:query] = {:filters => {'status_id' => {:values => [''], :operator => 'o'}}, :project_id => 1}
1043 1048 @request.session['issues_index_sort'] = 'id'
1044 1049
1045 1050 with_settings :display_subprojects_issues => '0' do
1046 1051 get :show, :id => 3
1047 1052 end
1048 1053
1049 1054 assert_response :success
1050 1055 # Previous and next issues inside project
1051 1056 assert_equal 2, assigns(:prev_issue_id)
1052 1057 assert_equal 7, assigns(:next_issue_id)
1053 1058
1054 1059 assert_tag 'a', :attributes => {:href => '/issues/2'}, :content => /Previous/
1055 1060 assert_tag 'a', :attributes => {:href => '/issues/7'}, :content => /Next/
1056 1061 end
1057 1062
1058 1063 def test_show_should_not_display_prev_link_for_first_issue
1059 1064 @request.session[:query] = {:filters => {'status_id' => {:values => [''], :operator => 'o'}}, :project_id => 1}
1060 1065 @request.session['issues_index_sort'] = 'id'
1061 1066
1062 1067 with_settings :display_subprojects_issues => '0' do
1063 1068 get :show, :id => 1
1064 1069 end
1065 1070
1066 1071 assert_response :success
1067 1072 assert_nil assigns(:prev_issue_id)
1068 1073 assert_equal 2, assigns(:next_issue_id)
1069 1074
1070 1075 assert_no_tag 'a', :content => /Previous/
1071 1076 assert_tag 'a', :attributes => {:href => '/issues/2'}, :content => /Next/
1072 1077 end
1073 1078
1074 1079 def test_show_should_not_display_prev_next_links_for_issue_not_in_query_results
1075 1080 @request.session[:query] = {:filters => {'status_id' => {:values => [''], :operator => 'c'}}, :project_id => 1}
1076 1081 @request.session['issues_index_sort'] = 'id'
1077 1082
1078 1083 get :show, :id => 1
1079 1084
1080 1085 assert_response :success
1081 1086 assert_nil assigns(:prev_issue_id)
1082 1087 assert_nil assigns(:next_issue_id)
1083 1088
1084 1089 assert_no_tag 'a', :content => /Previous/
1085 1090 assert_no_tag 'a', :content => /Next/
1086 1091 end
1087 1092
1088 1093 def test_show_should_display_visible_changesets_from_other_projects
1089 1094 project = Project.find(2)
1090 1095 issue = project.issues.first
1091 1096 issue.changeset_ids = [102]
1092 1097 issue.save!
1093 1098 project.disable_module! :repository
1094 1099
1095 1100 @request.session[:user_id] = 2
1096 1101 get :show, :id => issue.id
1097 1102 assert_tag 'a', :attributes => {:href => "/projects/ecookbook/repository/revisions/3"}
1098 1103 end
1099 1104
1100 1105 def test_show_with_multi_custom_field
1101 1106 field = CustomField.find(1)
1102 1107 field.update_attribute :multiple, true
1103 1108 issue = Issue.find(1)
1104 1109 issue.custom_field_values = {1 => ['MySQL', 'Oracle']}
1105 1110 issue.save!
1106 1111
1107 1112 get :show, :id => 1
1108 1113 assert_response :success
1109 1114
1110 1115 assert_tag :td, :content => 'MySQL, Oracle'
1111 1116 end
1112 1117
1113 1118 def test_show_with_multi_user_custom_field
1114 1119 field = IssueCustomField.create!(:name => 'Multi user', :field_format => 'user', :multiple => true,
1115 1120 :tracker_ids => [1], :is_for_all => true)
1116 1121 issue = Issue.find(1)
1117 1122 issue.custom_field_values = {field.id => ['2', '3']}
1118 1123 issue.save!
1119 1124
1120 1125 get :show, :id => 1
1121 1126 assert_response :success
1122 1127
1123 1128 # TODO: should display links
1124 1129 assert_tag :td, :content => 'Dave Lopper, John Smith'
1125 1130 end
1126 1131
1127 1132 def test_show_atom
1128 1133 get :show, :id => 2, :format => 'atom'
1129 1134 assert_response :success
1130 1135 assert_template 'journals/index'
1131 1136 # Inline image
1132 1137 assert_select 'content', :text => Regexp.new(Regexp.quote('http://test.host/attachments/download/10'))
1133 1138 end
1134 1139
1135 1140 def test_show_export_to_pdf
1136 1141 get :show, :id => 3, :format => 'pdf'
1137 1142 assert_response :success
1138 1143 assert_equal 'application/pdf', @response.content_type
1139 1144 assert @response.body.starts_with?('%PDF')
1140 1145 assert_not_nil assigns(:issue)
1141 1146 end
1142 1147
1143 1148 def test_get_new
1144 1149 @request.session[:user_id] = 2
1145 1150 get :new, :project_id => 1, :tracker_id => 1
1146 1151 assert_response :success
1147 1152 assert_template 'new'
1148 1153
1149 1154 assert_tag 'input', :attributes => {:name => 'issue[is_private]'}
1150 1155 assert_no_tag 'select', :attributes => {:name => 'issue[project_id]'}
1151 1156 assert_tag 'select', :attributes => {:name => 'issue[tracker_id]'}
1152 1157 assert_tag 'input', :attributes => {:name => 'issue[subject]'}
1153 1158 assert_tag 'textarea', :attributes => {:name => 'issue[description]'}
1154 1159 assert_tag 'select', :attributes => {:name => 'issue[status_id]'}
1155 1160 assert_tag 'select', :attributes => {:name => 'issue[priority_id]'}
1156 1161 assert_tag 'select', :attributes => {:name => 'issue[assigned_to_id]'}
1157 1162 assert_tag 'select', :attributes => {:name => 'issue[category_id]'}
1158 1163 assert_tag 'select', :attributes => {:name => 'issue[fixed_version_id]'}
1159 1164 assert_tag 'input', :attributes => {:name => 'issue[parent_issue_id]'}
1160 1165 assert_tag 'input', :attributes => {:name => 'issue[start_date]'}
1161 1166 assert_tag 'input', :attributes => {:name => 'issue[due_date]'}
1162 1167 assert_tag 'select', :attributes => {:name => 'issue[done_ratio]'}
1163 1168 assert_tag 'input', :attributes => { :name => 'issue[custom_field_values][2]', :value => 'Default string' }
1164 1169 assert_tag 'input', :attributes => {:name => 'issue[watcher_user_ids][]'}
1165 1170
1166 1171 # Be sure we don't display inactive IssuePriorities
1167 1172 assert ! IssuePriority.find(15).active?
1168 1173 assert_no_tag :option, :attributes => {:value => '15'},
1169 1174 :parent => {:tag => 'select', :attributes => {:id => 'issue_priority_id'} }
1170 1175 end
1171 1176
1172 1177 def test_get_new_with_minimal_permissions
1173 1178 Role.find(1).update_attribute :permissions, [:add_issues]
1174 1179 Workflow.delete_all :role_id => 1
1175 1180
1176 1181 @request.session[:user_id] = 2
1177 1182 get :new, :project_id => 1, :tracker_id => 1
1178 1183 assert_response :success
1179 1184 assert_template 'new'
1180 1185
1181 1186 assert_no_tag 'input', :attributes => {:name => 'issue[is_private]'}
1182 1187 assert_no_tag 'select', :attributes => {:name => 'issue[project_id]'}
1183 1188 assert_tag 'select', :attributes => {:name => 'issue[tracker_id]'}
1184 1189 assert_tag 'input', :attributes => {:name => 'issue[subject]'}
1185 1190 assert_tag 'textarea', :attributes => {:name => 'issue[description]'}
1186 1191 assert_tag 'select', :attributes => {:name => 'issue[status_id]'}
1187 1192 assert_tag 'select', :attributes => {:name => 'issue[priority_id]'}
1188 1193 assert_tag 'select', :attributes => {:name => 'issue[assigned_to_id]'}
1189 1194 assert_tag 'select', :attributes => {:name => 'issue[category_id]'}
1190 1195 assert_tag 'select', :attributes => {:name => 'issue[fixed_version_id]'}
1191 1196 assert_no_tag 'input', :attributes => {:name => 'issue[parent_issue_id]'}
1192 1197 assert_tag 'input', :attributes => {:name => 'issue[start_date]'}
1193 1198 assert_tag 'input', :attributes => {:name => 'issue[due_date]'}
1194 1199 assert_tag 'select', :attributes => {:name => 'issue[done_ratio]'}
1195 1200 assert_tag 'input', :attributes => { :name => 'issue[custom_field_values][2]', :value => 'Default string' }
1196 1201 assert_no_tag 'input', :attributes => {:name => 'issue[watcher_user_ids][]'}
1197 1202 end
1198 1203
1199 1204 def test_get_new_with_list_custom_field
1200 1205 @request.session[:user_id] = 2
1201 1206 get :new, :project_id => 1, :tracker_id => 1
1202 1207 assert_response :success
1203 1208 assert_template 'new'
1204 1209
1205 1210 assert_tag 'select',
1206 1211 :attributes => {:name => 'issue[custom_field_values][1]'},
1207 1212 :children => {:count => 4},
1208 1213 :child => {:tag => 'option', :attributes => {:value => 'MySQL'}, :content => 'MySQL'}
1209 1214 end
1210 1215
1211 1216 def test_get_new_with_multi_custom_field
1212 1217 field = IssueCustomField.find(1)
1213 1218 field.update_attribute :multiple, true
1214 1219
1215 1220 @request.session[:user_id] = 2
1216 1221 get :new, :project_id => 1, :tracker_id => 1
1217 1222 assert_response :success
1218 1223 assert_template 'new'
1219 1224
1220 1225 assert_tag 'select',
1221 1226 :attributes => {:name => 'issue[custom_field_values][1][]', :multiple => 'multiple'},
1222 1227 :children => {:count => 3},
1223 1228 :child => {:tag => 'option', :attributes => {:value => 'MySQL'}, :content => 'MySQL'}
1224 1229 assert_tag 'input',
1225 1230 :attributes => {:name => 'issue[custom_field_values][1][]', :value => ''}
1226 1231 end
1227 1232
1228 1233 def test_get_new_with_multi_user_custom_field
1229 1234 field = IssueCustomField.create!(:name => 'Multi user', :field_format => 'user', :multiple => true,
1230 1235 :tracker_ids => [1], :is_for_all => true)
1231 1236
1232 1237 @request.session[:user_id] = 2
1233 1238 get :new, :project_id => 1, :tracker_id => 1
1234 1239 assert_response :success
1235 1240 assert_template 'new'
1236 1241
1237 1242 assert_tag 'select',
1238 1243 :attributes => {:name => "issue[custom_field_values][#{field.id}][]", :multiple => 'multiple'},
1239 1244 :children => {:count => Project.find(1).users.count},
1240 1245 :child => {:tag => 'option', :attributes => {:value => '2'}, :content => 'John Smith'}
1241 1246 assert_tag 'input',
1242 1247 :attributes => {:name => "issue[custom_field_values][#{field.id}][]", :value => ''}
1243 1248 end
1244 1249
1245 1250 def test_get_new_without_default_start_date_is_creation_date
1246 1251 Setting.default_issue_start_date_to_creation_date = 0
1247 1252
1248 1253 @request.session[:user_id] = 2
1249 1254 get :new, :project_id => 1, :tracker_id => 1
1250 1255 assert_response :success
1251 1256 assert_template 'new'
1252 1257
1253 1258 assert_tag :tag => 'input', :attributes => { :name => 'issue[start_date]',
1254 1259 :value => nil }
1255 1260 end
1256 1261
1257 1262 def test_get_new_with_default_start_date_is_creation_date
1258 1263 Setting.default_issue_start_date_to_creation_date = 1
1259 1264
1260 1265 @request.session[:user_id] = 2
1261 1266 get :new, :project_id => 1, :tracker_id => 1
1262 1267 assert_response :success
1263 1268 assert_template 'new'
1264 1269
1265 1270 assert_tag :tag => 'input', :attributes => { :name => 'issue[start_date]',
1266 1271 :value => Date.today.to_s }
1267 1272 end
1268 1273
1269 1274 def test_get_new_form_should_allow_attachment_upload
1270 1275 @request.session[:user_id] = 2
1271 1276 get :new, :project_id => 1, :tracker_id => 1
1272 1277
1273 1278 assert_tag :tag => 'form',
1274 1279 :attributes => {:id => 'issue-form', :method => 'post', :enctype => 'multipart/form-data'},
1275 1280 :descendant => {
1276 1281 :tag => 'input',
1277 1282 :attributes => {:type => 'file', :name => 'attachments[1][file]'}
1278 1283 }
1279 1284 end
1280 1285
1281 1286 def test_get_new_without_tracker_id
1282 1287 @request.session[:user_id] = 2
1283 1288 get :new, :project_id => 1
1284 1289 assert_response :success
1285 1290 assert_template 'new'
1286 1291
1287 1292 issue = assigns(:issue)
1288 1293 assert_not_nil issue
1289 1294 assert_equal Project.find(1).trackers.first, issue.tracker
1290 1295 end
1291 1296
1292 1297 def test_get_new_with_no_default_status_should_display_an_error
1293 1298 @request.session[:user_id] = 2
1294 1299 IssueStatus.delete_all
1295 1300
1296 1301 get :new, :project_id => 1
1297 1302 assert_response 500
1298 1303 assert_error_tag :content => /No default issue/
1299 1304 end
1300 1305
1301 1306 def test_get_new_with_no_tracker_should_display_an_error
1302 1307 @request.session[:user_id] = 2
1303 1308 Tracker.delete_all
1304 1309
1305 1310 get :new, :project_id => 1
1306 1311 assert_response 500
1307 1312 assert_error_tag :content => /No tracker/
1308 1313 end
1309 1314
1310 1315 def test_update_new_form
1311 1316 @request.session[:user_id] = 2
1312 1317 xhr :post, :new, :project_id => 1,
1313 1318 :issue => {:tracker_id => 2,
1314 1319 :subject => 'This is the test_new issue',
1315 1320 :description => 'This is the description',
1316 1321 :priority_id => 5}
1317 1322 assert_response :success
1318 1323 assert_template 'attributes'
1319 1324
1320 1325 issue = assigns(:issue)
1321 1326 assert_kind_of Issue, issue
1322 1327 assert_equal 1, issue.project_id
1323 1328 assert_equal 2, issue.tracker_id
1324 1329 assert_equal 'This is the test_new issue', issue.subject
1325 1330 end
1326 1331
1327 1332 def test_post_create
1328 1333 @request.session[:user_id] = 2
1329 1334 assert_difference 'Issue.count' do
1330 1335 post :create, :project_id => 1,
1331 1336 :issue => {:tracker_id => 3,
1332 1337 :status_id => 2,
1333 1338 :subject => 'This is the test_new issue',
1334 1339 :description => 'This is the description',
1335 1340 :priority_id => 5,
1336 1341 :start_date => '2010-11-07',
1337 1342 :estimated_hours => '',
1338 1343 :custom_field_values => {'2' => 'Value for field 2'}}
1339 1344 end
1340 1345 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1341 1346
1342 1347 issue = Issue.find_by_subject('This is the test_new issue')
1343 1348 assert_not_nil issue
1344 1349 assert_equal 2, issue.author_id
1345 1350 assert_equal 3, issue.tracker_id
1346 1351 assert_equal 2, issue.status_id
1347 1352 assert_equal Date.parse('2010-11-07'), issue.start_date
1348 1353 assert_nil issue.estimated_hours
1349 1354 v = issue.custom_values.find(:first, :conditions => {:custom_field_id => 2})
1350 1355 assert_not_nil v
1351 1356 assert_equal 'Value for field 2', v.value
1352 1357 end
1353 1358
1354 1359 def test_post_new_with_group_assignment
1355 1360 group = Group.find(11)
1356 1361 project = Project.find(1)
1357 1362 project.members << Member.new(:principal => group, :roles => [Role.givable.first])
1358 1363
1359 1364 with_settings :issue_group_assignment => '1' do
1360 1365 @request.session[:user_id] = 2
1361 1366 assert_difference 'Issue.count' do
1362 1367 post :create, :project_id => project.id,
1363 1368 :issue => {:tracker_id => 3,
1364 1369 :status_id => 1,
1365 1370 :subject => 'This is the test_new_with_group_assignment issue',
1366 1371 :assigned_to_id => group.id}
1367 1372 end
1368 1373 end
1369 1374 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1370 1375
1371 1376 issue = Issue.find_by_subject('This is the test_new_with_group_assignment issue')
1372 1377 assert_not_nil issue
1373 1378 assert_equal group, issue.assigned_to
1374 1379 end
1375 1380
1376 1381 def test_post_create_without_start_date_and_default_start_date_is_not_creation_date
1377 1382 Setting.default_issue_start_date_to_creation_date = 0
1378 1383
1379 1384 @request.session[:user_id] = 2
1380 1385 assert_difference 'Issue.count' do
1381 1386 post :create, :project_id => 1,
1382 1387 :issue => {:tracker_id => 3,
1383 1388 :status_id => 2,
1384 1389 :subject => 'This is the test_new issue',
1385 1390 :description => 'This is the description',
1386 1391 :priority_id => 5,
1387 1392 :estimated_hours => '',
1388 1393 :custom_field_values => {'2' => 'Value for field 2'}}
1389 1394 end
1390 1395 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1391 1396
1392 1397 issue = Issue.find_by_subject('This is the test_new issue')
1393 1398 assert_not_nil issue
1394 1399 assert_nil issue.start_date
1395 1400 end
1396 1401
1397 1402 def test_post_create_without_start_date_and_default_start_date_is_creation_date
1398 1403 Setting.default_issue_start_date_to_creation_date = 1
1399 1404
1400 1405 @request.session[:user_id] = 2
1401 1406 assert_difference 'Issue.count' do
1402 1407 post :create, :project_id => 1,
1403 1408 :issue => {:tracker_id => 3,
1404 1409 :status_id => 2,
1405 1410 :subject => 'This is the test_new issue',
1406 1411 :description => 'This is the description',
1407 1412 :priority_id => 5,
1408 1413 :estimated_hours => '',
1409 1414 :custom_field_values => {'2' => 'Value for field 2'}}
1410 1415 end
1411 1416 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1412 1417
1413 1418 issue = Issue.find_by_subject('This is the test_new issue')
1414 1419 assert_not_nil issue
1415 1420 assert_equal Date.today, issue.start_date
1416 1421 end
1417 1422
1418 1423 def test_post_create_and_continue
1419 1424 @request.session[:user_id] = 2
1420 1425 assert_difference 'Issue.count' do
1421 1426 post :create, :project_id => 1,
1422 1427 :issue => {:tracker_id => 3, :subject => 'This is first issue', :priority_id => 5},
1423 1428 :continue => ''
1424 1429 end
1425 1430
1426 1431 issue = Issue.first(:order => 'id DESC')
1427 1432 assert_redirected_to :controller => 'issues', :action => 'new', :project_id => 'ecookbook', :issue => {:tracker_id => 3}
1428 1433 assert_not_nil flash[:notice], "flash was not set"
1429 1434 assert flash[:notice].include?("<a href='/issues/#{issue.id}'>##{issue.id}</a>"), "issue link not found in flash: #{flash[:notice]}"
1430 1435 end
1431 1436
1432 1437 def test_post_create_without_custom_fields_param
1433 1438 @request.session[:user_id] = 2
1434 1439 assert_difference 'Issue.count' do
1435 1440 post :create, :project_id => 1,
1436 1441 :issue => {:tracker_id => 1,
1437 1442 :subject => 'This is the test_new issue',
1438 1443 :description => 'This is the description',
1439 1444 :priority_id => 5}
1440 1445 end
1441 1446 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1442 1447 end
1443 1448
1444 1449 def test_post_create_with_multi_custom_field
1445 1450 field = IssueCustomField.find_by_name('Database')
1446 1451 field.update_attribute(:multiple, true)
1447 1452
1448 1453 @request.session[:user_id] = 2
1449 1454 assert_difference 'Issue.count' do
1450 1455 post :create, :project_id => 1,
1451 1456 :issue => {:tracker_id => 1,
1452 1457 :subject => 'This is the test_new issue',
1453 1458 :description => 'This is the description',
1454 1459 :priority_id => 5,
1455 1460 :custom_field_values => {'1' => ['', 'MySQL', 'Oracle']}}
1456 1461 end
1457 1462 assert_response 302
1458 1463 issue = Issue.first(:order => 'id DESC')
1459 1464 assert_equal ['MySQL', 'Oracle'], issue.custom_field_value(1).sort
1460 1465 end
1461 1466
1462 1467 def test_post_create_with_empty_multi_custom_field
1463 1468 field = IssueCustomField.find_by_name('Database')
1464 1469 field.update_attribute(:multiple, true)
1465 1470
1466 1471 @request.session[:user_id] = 2
1467 1472 assert_difference 'Issue.count' do
1468 1473 post :create, :project_id => 1,
1469 1474 :issue => {:tracker_id => 1,
1470 1475 :subject => 'This is the test_new issue',
1471 1476 :description => 'This is the description',
1472 1477 :priority_id => 5,
1473 1478 :custom_field_values => {'1' => ['']}}
1474 1479 end
1475 1480 assert_response 302
1476 1481 issue = Issue.first(:order => 'id DESC')
1477 1482 assert_equal [''], issue.custom_field_value(1).sort
1478 1483 end
1479 1484
1480 1485 def test_post_create_with_multi_user_custom_field
1481 1486 field = IssueCustomField.create!(:name => 'Multi user', :field_format => 'user', :multiple => true,
1482 1487 :tracker_ids => [1], :is_for_all => true)
1483 1488
1484 1489 @request.session[:user_id] = 2
1485 1490 assert_difference 'Issue.count' do
1486 1491 post :create, :project_id => 1,
1487 1492 :issue => {:tracker_id => 1,
1488 1493 :subject => 'This is the test_new issue',
1489 1494 :description => 'This is the description',
1490 1495 :priority_id => 5,
1491 1496 :custom_field_values => {field.id.to_s => ['', '2', '3']}}
1492 1497 end
1493 1498 assert_response 302
1494 1499 issue = Issue.first(:order => 'id DESC')
1495 1500 assert_equal ['2', '3'], issue.custom_field_value(field).sort
1496 1501 end
1497 1502
1498 1503 def test_post_create_with_required_custom_field_and_without_custom_fields_param
1499 1504 field = IssueCustomField.find_by_name('Database')
1500 1505 field.update_attribute(:is_required, true)
1501 1506
1502 1507 @request.session[:user_id] = 2
1503 1508 assert_no_difference 'Issue.count' do
1504 1509 post :create, :project_id => 1,
1505 1510 :issue => {:tracker_id => 1,
1506 1511 :subject => 'This is the test_new issue',
1507 1512 :description => 'This is the description',
1508 1513 :priority_id => 5}
1509 1514 end
1510 1515 assert_response :success
1511 1516 assert_template 'new'
1512 1517 issue = assigns(:issue)
1513 1518 assert_not_nil issue
1514 1519 assert_error_tag :content => /Database can't be blank/
1515 1520 end
1516 1521
1517 1522 def test_post_create_with_watchers
1518 1523 @request.session[:user_id] = 2
1519 1524 ActionMailer::Base.deliveries.clear
1520 1525
1521 1526 assert_difference 'Watcher.count', 2 do
1522 1527 post :create, :project_id => 1,
1523 1528 :issue => {:tracker_id => 1,
1524 1529 :subject => 'This is a new issue with watchers',
1525 1530 :description => 'This is the description',
1526 1531 :priority_id => 5,
1527 1532 :watcher_user_ids => ['2', '3']}
1528 1533 end
1529 1534 issue = Issue.find_by_subject('This is a new issue with watchers')
1530 1535 assert_not_nil issue
1531 1536 assert_redirected_to :controller => 'issues', :action => 'show', :id => issue
1532 1537
1533 1538 # Watchers added
1534 1539 assert_equal [2, 3], issue.watcher_user_ids.sort
1535 1540 assert issue.watched_by?(User.find(3))
1536 1541 # Watchers notified
1537 1542 mail = ActionMailer::Base.deliveries.last
1538 1543 assert_not_nil mail
1539 1544 assert [mail.bcc, mail.cc].flatten.include?(User.find(3).mail)
1540 1545 end
1541 1546
1542 1547 def test_post_create_subissue
1543 1548 @request.session[:user_id] = 2
1544 1549
1545 1550 assert_difference 'Issue.count' do
1546 1551 post :create, :project_id => 1,
1547 1552 :issue => {:tracker_id => 1,
1548 1553 :subject => 'This is a child issue',
1549 1554 :parent_issue_id => 2}
1550 1555 end
1551 1556 issue = Issue.find_by_subject('This is a child issue')
1552 1557 assert_not_nil issue
1553 1558 assert_equal Issue.find(2), issue.parent
1554 1559 end
1555 1560
1556 1561 def test_post_create_subissue_with_non_numeric_parent_id
1557 1562 @request.session[:user_id] = 2
1558 1563
1559 1564 assert_difference 'Issue.count' do
1560 1565 post :create, :project_id => 1,
1561 1566 :issue => {:tracker_id => 1,
1562 1567 :subject => 'This is a child issue',
1563 1568 :parent_issue_id => 'ABC'}
1564 1569 end
1565 1570 issue = Issue.find_by_subject('This is a child issue')
1566 1571 assert_not_nil issue
1567 1572 assert_nil issue.parent
1568 1573 end
1569 1574
1570 1575 def test_post_create_private
1571 1576 @request.session[:user_id] = 2
1572 1577
1573 1578 assert_difference 'Issue.count' do
1574 1579 post :create, :project_id => 1,
1575 1580 :issue => {:tracker_id => 1,
1576 1581 :subject => 'This is a private issue',
1577 1582 :is_private => '1'}
1578 1583 end
1579 1584 issue = Issue.first(:order => 'id DESC')
1580 1585 assert issue.is_private?
1581 1586 end
1582 1587
1583 1588 def test_post_create_private_with_set_own_issues_private_permission
1584 1589 role = Role.find(1)
1585 1590 role.remove_permission! :set_issues_private
1586 1591 role.add_permission! :set_own_issues_private
1587 1592
1588 1593 @request.session[:user_id] = 2
1589 1594
1590 1595 assert_difference 'Issue.count' do
1591 1596 post :create, :project_id => 1,
1592 1597 :issue => {:tracker_id => 1,
1593 1598 :subject => 'This is a private issue',
1594 1599 :is_private => '1'}
1595 1600 end
1596 1601 issue = Issue.first(:order => 'id DESC')
1597 1602 assert issue.is_private?
1598 1603 end
1599 1604
1600 1605 def test_post_create_should_send_a_notification
1601 1606 ActionMailer::Base.deliveries.clear
1602 1607 @request.session[:user_id] = 2
1603 1608 assert_difference 'Issue.count' do
1604 1609 post :create, :project_id => 1,
1605 1610 :issue => {:tracker_id => 3,
1606 1611 :subject => 'This is the test_new issue',
1607 1612 :description => 'This is the description',
1608 1613 :priority_id => 5,
1609 1614 :estimated_hours => '',
1610 1615 :custom_field_values => {'2' => 'Value for field 2'}}
1611 1616 end
1612 1617 assert_redirected_to :controller => 'issues', :action => 'show', :id => Issue.last.id
1613 1618
1614 1619 assert_equal 1, ActionMailer::Base.deliveries.size
1615 1620 end
1616 1621
1617 1622 def test_post_create_should_preserve_fields_values_on_validation_failure
1618 1623 @request.session[:user_id] = 2
1619 1624 post :create, :project_id => 1,
1620 1625 :issue => {:tracker_id => 1,
1621 1626 # empty subject
1622 1627 :subject => '',
1623 1628 :description => 'This is a description',
1624 1629 :priority_id => 6,
1625 1630 :custom_field_values => {'1' => 'Oracle', '2' => 'Value for field 2'}}
1626 1631 assert_response :success
1627 1632 assert_template 'new'
1628 1633
1629 1634 assert_tag :textarea, :attributes => { :name => 'issue[description]' },
1630 1635 :content => 'This is a description'
1631 1636 assert_tag :select, :attributes => { :name => 'issue[priority_id]' },
1632 1637 :child => { :tag => 'option', :attributes => { :selected => 'selected',
1633 1638 :value => '6' },
1634 1639 :content => 'High' }
1635 1640 # Custom fields
1636 1641 assert_tag :select, :attributes => { :name => 'issue[custom_field_values][1]' },
1637 1642 :child => { :tag => 'option', :attributes => { :selected => 'selected',
1638 1643 :value => 'Oracle' },
1639 1644 :content => 'Oracle' }
1640 1645 assert_tag :input, :attributes => { :name => 'issue[custom_field_values][2]',
1641 1646 :value => 'Value for field 2'}
1642 1647 end
1643 1648
1644 1649 def test_post_create_should_ignore_non_safe_attributes
1645 1650 @request.session[:user_id] = 2
1646 1651 assert_nothing_raised do
1647 1652 post :create, :project_id => 1, :issue => { :tracker => "A param can not be a Tracker" }
1648 1653 end
1649 1654 end
1650 1655
1651 1656 def test_post_create_with_attachment
1652 1657 set_tmp_attachments_directory
1653 1658 @request.session[:user_id] = 2
1654 1659
1655 1660 assert_difference 'Issue.count' do
1656 1661 assert_difference 'Attachment.count' do
1657 1662 post :create, :project_id => 1,
1658 1663 :issue => { :tracker_id => '1', :subject => 'With attachment' },
1659 1664 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain'), 'description' => 'test file'}}
1660 1665 end
1661 1666 end
1662 1667
1663 1668 issue = Issue.first(:order => 'id DESC')
1664 1669 attachment = Attachment.first(:order => 'id DESC')
1665 1670
1666 1671 assert_equal issue, attachment.container
1667 1672 assert_equal 2, attachment.author_id
1668 1673 assert_equal 'testfile.txt', attachment.filename
1669 1674 assert_equal 'text/plain', attachment.content_type
1670 1675 assert_equal 'test file', attachment.description
1671 1676 assert_equal 59, attachment.filesize
1672 1677 assert File.exists?(attachment.diskfile)
1673 1678 assert_equal 59, File.size(attachment.diskfile)
1674 1679 end
1675 1680
1676 1681 def test_post_create_with_failure_should_save_attachments
1677 1682 set_tmp_attachments_directory
1678 1683 @request.session[:user_id] = 2
1679 1684
1680 1685 assert_no_difference 'Issue.count' do
1681 1686 assert_difference 'Attachment.count' do
1682 1687 post :create, :project_id => 1,
1683 1688 :issue => { :tracker_id => '1', :subject => '' },
1684 1689 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain'), 'description' => 'test file'}}
1685 1690 assert_response :success
1686 1691 assert_template 'new'
1687 1692 end
1688 1693 end
1689 1694
1690 1695 attachment = Attachment.first(:order => 'id DESC')
1691 1696 assert_equal 'testfile.txt', attachment.filename
1692 1697 assert File.exists?(attachment.diskfile)
1693 1698 assert_nil attachment.container
1694 1699
1695 1700 assert_tag 'input', :attributes => {:name => 'attachments[p0][token]', :value => attachment.token}
1696 1701 assert_tag 'span', :content => /testfile.txt/
1697 1702 end
1698 1703
1699 1704 def test_post_create_with_failure_should_keep_saved_attachments
1700 1705 set_tmp_attachments_directory
1701 1706 attachment = Attachment.create!(:file => uploaded_test_file("testfile.txt", "text/plain"), :author_id => 2)
1702 1707 @request.session[:user_id] = 2
1703 1708
1704 1709 assert_no_difference 'Issue.count' do
1705 1710 assert_no_difference 'Attachment.count' do
1706 1711 post :create, :project_id => 1,
1707 1712 :issue => { :tracker_id => '1', :subject => '' },
1708 1713 :attachments => {'p0' => {'token' => attachment.token}}
1709 1714 assert_response :success
1710 1715 assert_template 'new'
1711 1716 end
1712 1717 end
1713 1718
1714 1719 assert_tag 'input', :attributes => {:name => 'attachments[p0][token]', :value => attachment.token}
1715 1720 assert_tag 'span', :content => /testfile.txt/
1716 1721 end
1717 1722
1718 1723 def test_post_create_should_attach_saved_attachments
1719 1724 set_tmp_attachments_directory
1720 1725 attachment = Attachment.create!(:file => uploaded_test_file("testfile.txt", "text/plain"), :author_id => 2)
1721 1726 @request.session[:user_id] = 2
1722 1727
1723 1728 assert_difference 'Issue.count' do
1724 1729 assert_no_difference 'Attachment.count' do
1725 1730 post :create, :project_id => 1,
1726 1731 :issue => { :tracker_id => '1', :subject => 'Saved attachments' },
1727 1732 :attachments => {'p0' => {'token' => attachment.token}}
1728 1733 assert_response 302
1729 1734 end
1730 1735 end
1731 1736
1732 1737 issue = Issue.first(:order => 'id DESC')
1733 1738 assert_equal 1, issue.attachments.count
1734 1739
1735 1740 attachment.reload
1736 1741 assert_equal issue, attachment.container
1737 1742 end
1738 1743
1739 1744 context "without workflow privilege" do
1740 1745 setup do
1741 1746 Workflow.delete_all(["role_id = ?", Role.anonymous.id])
1742 1747 Role.anonymous.add_permission! :add_issues, :add_issue_notes
1743 1748 end
1744 1749
1745 1750 context "#new" do
1746 1751 should "propose default status only" do
1747 1752 get :new, :project_id => 1
1748 1753 assert_response :success
1749 1754 assert_template 'new'
1750 1755 assert_tag :tag => 'select',
1751 1756 :attributes => {:name => 'issue[status_id]'},
1752 1757 :children => {:count => 1},
1753 1758 :child => {:tag => 'option', :attributes => {:value => IssueStatus.default.id.to_s}}
1754 1759 end
1755 1760
1756 1761 should "accept default status" do
1757 1762 assert_difference 'Issue.count' do
1758 1763 post :create, :project_id => 1,
1759 1764 :issue => {:tracker_id => 1,
1760 1765 :subject => 'This is an issue',
1761 1766 :status_id => 1}
1762 1767 end
1763 1768 issue = Issue.last(:order => 'id')
1764 1769 assert_equal IssueStatus.default, issue.status
1765 1770 end
1766 1771
1767 1772 should "ignore unauthorized status" do
1768 1773 assert_difference 'Issue.count' do
1769 1774 post :create, :project_id => 1,
1770 1775 :issue => {:tracker_id => 1,
1771 1776 :subject => 'This is an issue',
1772 1777 :status_id => 3}
1773 1778 end
1774 1779 issue = Issue.last(:order => 'id')
1775 1780 assert_equal IssueStatus.default, issue.status
1776 1781 end
1777 1782 end
1778 1783
1779 1784 context "#update" do
1780 1785 should "ignore status change" do
1781 1786 assert_difference 'Journal.count' do
1782 1787 put :update, :id => 1, :notes => 'just trying', :issue => {:status_id => 3}
1783 1788 end
1784 1789 assert_equal 1, Issue.find(1).status_id
1785 1790 end
1786 1791
1787 1792 should "ignore attributes changes" do
1788 1793 assert_difference 'Journal.count' do
1789 1794 put :update, :id => 1, :notes => 'just trying', :issue => {:subject => 'changed', :assigned_to_id => 2}
1790 1795 end
1791 1796 issue = Issue.find(1)
1792 1797 assert_equal "Can't print recipes", issue.subject
1793 1798 assert_nil issue.assigned_to
1794 1799 end
1795 1800 end
1796 1801 end
1797 1802
1798 1803 context "with workflow privilege" do
1799 1804 setup do
1800 1805 Workflow.delete_all(["role_id = ?", Role.anonymous.id])
1801 1806 Workflow.create!(:role => Role.anonymous, :tracker_id => 1, :old_status_id => 1, :new_status_id => 3)
1802 1807 Workflow.create!(:role => Role.anonymous, :tracker_id => 1, :old_status_id => 1, :new_status_id => 4)
1803 1808 Role.anonymous.add_permission! :add_issues, :add_issue_notes
1804 1809 end
1805 1810
1806 1811 context "#update" do
1807 1812 should "accept authorized status" do
1808 1813 assert_difference 'Journal.count' do
1809 1814 put :update, :id => 1, :notes => 'just trying', :issue => {:status_id => 3}
1810 1815 end
1811 1816 assert_equal 3, Issue.find(1).status_id
1812 1817 end
1813 1818
1814 1819 should "ignore unauthorized status" do
1815 1820 assert_difference 'Journal.count' do
1816 1821 put :update, :id => 1, :notes => 'just trying', :issue => {:status_id => 2}
1817 1822 end
1818 1823 assert_equal 1, Issue.find(1).status_id
1819 1824 end
1820 1825
1821 1826 should "accept authorized attributes changes" do
1822 1827 assert_difference 'Journal.count' do
1823 1828 put :update, :id => 1, :notes => 'just trying', :issue => {:assigned_to_id => 2}
1824 1829 end
1825 1830 issue = Issue.find(1)
1826 1831 assert_equal 2, issue.assigned_to_id
1827 1832 end
1828 1833
1829 1834 should "ignore unauthorized attributes changes" do
1830 1835 assert_difference 'Journal.count' do
1831 1836 put :update, :id => 1, :notes => 'just trying', :issue => {:subject => 'changed'}
1832 1837 end
1833 1838 issue = Issue.find(1)
1834 1839 assert_equal "Can't print recipes", issue.subject
1835 1840 end
1836 1841 end
1837 1842
1838 1843 context "and :edit_issues permission" do
1839 1844 setup do
1840 1845 Role.anonymous.add_permission! :add_issues, :edit_issues
1841 1846 end
1842 1847
1843 1848 should "accept authorized status" do
1844 1849 assert_difference 'Journal.count' do
1845 1850 put :update, :id => 1, :notes => 'just trying', :issue => {:status_id => 3}
1846 1851 end
1847 1852 assert_equal 3, Issue.find(1).status_id
1848 1853 end
1849 1854
1850 1855 should "ignore unauthorized status" do
1851 1856 assert_difference 'Journal.count' do
1852 1857 put :update, :id => 1, :notes => 'just trying', :issue => {:status_id => 2}
1853 1858 end
1854 1859 assert_equal 1, Issue.find(1).status_id
1855 1860 end
1856 1861
1857 1862 should "accept authorized attributes changes" do
1858 1863 assert_difference 'Journal.count' do
1859 1864 put :update, :id => 1, :notes => 'just trying', :issue => {:subject => 'changed', :assigned_to_id => 2}
1860 1865 end
1861 1866 issue = Issue.find(1)
1862 1867 assert_equal "changed", issue.subject
1863 1868 assert_equal 2, issue.assigned_to_id
1864 1869 end
1865 1870 end
1866 1871 end
1867 1872
1868 1873 def test_new_as_copy
1869 1874 @request.session[:user_id] = 2
1870 1875 get :new, :project_id => 1, :copy_from => 1
1871 1876
1872 1877 assert_response :success
1873 1878 assert_template 'new'
1874 1879
1875 1880 assert_not_nil assigns(:issue)
1876 1881 orig = Issue.find(1)
1877 1882 assert_equal 1, assigns(:issue).project_id
1878 1883 assert_equal orig.subject, assigns(:issue).subject
1879 1884 assert assigns(:issue).copy?
1880 1885
1881 1886 assert_tag 'form', :attributes => {:id => 'issue-form', :action => '/projects/ecookbook/issues'}
1882 1887 assert_tag 'select', :attributes => {:name => 'issue[project_id]'}
1883 1888 assert_tag 'select', :attributes => {:name => 'issue[project_id]'},
1884 1889 :child => {:tag => 'option', :attributes => {:value => '1', :selected => 'selected'}, :content => 'eCookbook'}
1885 1890 assert_tag 'select', :attributes => {:name => 'issue[project_id]'},
1886 1891 :child => {:tag => 'option', :attributes => {:value => '2', :selected => nil}, :content => 'OnlineStore'}
1887 1892 assert_tag 'input', :attributes => {:name => 'copy_from', :value => '1'}
1888 1893 end
1889 1894
1890 1895 def test_new_as_copy_with_attachments_should_show_copy_attachments_checkbox
1891 1896 @request.session[:user_id] = 2
1892 1897 issue = Issue.find(3)
1893 1898 assert issue.attachments.count > 0
1894 1899 get :new, :project_id => 1, :copy_from => 3
1895 1900
1896 1901 assert_tag 'input', :attributes => {:name => 'copy_attachments', :type => 'checkbox', :checked => 'checked', :value => '1'}
1897 1902 end
1898 1903
1899 1904 def test_new_as_copy_without_attachments_should_not_show_copy_attachments_checkbox
1900 1905 @request.session[:user_id] = 2
1901 1906 issue = Issue.find(3)
1902 1907 issue.attachments.delete_all
1903 1908 get :new, :project_id => 1, :copy_from => 3
1904 1909
1905 1910 assert_no_tag 'input', :attributes => {:name => 'copy_attachments', :type => 'checkbox', :checked => 'checked', :value => '1'}
1906 1911 end
1907 1912
1908 1913 def test_new_as_copy_with_invalid_issue_should_respond_with_404
1909 1914 @request.session[:user_id] = 2
1910 1915 get :new, :project_id => 1, :copy_from => 99999
1911 1916 assert_response 404
1912 1917 end
1913 1918
1914 1919 def test_create_as_copy_on_different_project
1915 1920 @request.session[:user_id] = 2
1916 1921 assert_difference 'Issue.count' do
1917 1922 post :create, :project_id => 1, :copy_from => 1,
1918 1923 :issue => {:project_id => '2', :tracker_id => '3', :status_id => '1', :subject => 'Copy'}
1919 1924
1920 1925 assert_not_nil assigns(:issue)
1921 1926 assert assigns(:issue).copy?
1922 1927 end
1923 1928 issue = Issue.first(:order => 'id DESC')
1924 1929 assert_redirected_to "/issues/#{issue.id}"
1925 1930
1926 1931 assert_equal 2, issue.project_id
1927 1932 assert_equal 3, issue.tracker_id
1928 1933 assert_equal 'Copy', issue.subject
1929 1934 end
1930 1935
1931 1936 def test_create_as_copy_should_copy_attachments
1932 1937 @request.session[:user_id] = 2
1933 1938 issue = Issue.find(3)
1934 1939 count = issue.attachments.count
1935 1940 assert count > 0
1936 1941
1937 1942 assert_difference 'Issue.count' do
1938 1943 assert_difference 'Attachment.count', count do
1939 1944 assert_no_difference 'Journal.count' do
1940 1945 post :create, :project_id => 1, :copy_from => 3,
1941 1946 :issue => {:project_id => '1', :tracker_id => '3', :status_id => '1', :subject => 'Copy with attachments'},
1942 1947 :copy_attachments => '1'
1943 1948 end
1944 1949 end
1945 1950 end
1946 1951 copy = Issue.first(:order => 'id DESC')
1947 1952 assert_equal count, copy.attachments.count
1948 1953 assert_equal issue.attachments.map(&:filename).sort, copy.attachments.map(&:filename).sort
1949 1954 end
1950 1955
1951 1956 def test_create_as_copy_without_copy_attachments_option_should_not_copy_attachments
1952 1957 @request.session[:user_id] = 2
1953 1958 issue = Issue.find(3)
1954 1959 count = issue.attachments.count
1955 1960 assert count > 0
1956 1961
1957 1962 assert_difference 'Issue.count' do
1958 1963 assert_no_difference 'Attachment.count' do
1959 1964 assert_no_difference 'Journal.count' do
1960 1965 post :create, :project_id => 1, :copy_from => 3,
1961 1966 :issue => {:project_id => '1', :tracker_id => '3', :status_id => '1', :subject => 'Copy with attachments'}
1962 1967 end
1963 1968 end
1964 1969 end
1965 1970 copy = Issue.first(:order => 'id DESC')
1966 1971 assert_equal 0, copy.attachments.count
1967 1972 end
1968 1973
1969 1974 def test_create_as_copy_with_attachments_should_add_new_files
1970 1975 @request.session[:user_id] = 2
1971 1976 issue = Issue.find(3)
1972 1977 count = issue.attachments.count
1973 1978 assert count > 0
1974 1979
1975 1980 assert_difference 'Issue.count' do
1976 1981 assert_difference 'Attachment.count', count + 1 do
1977 1982 assert_no_difference 'Journal.count' do
1978 1983 post :create, :project_id => 1, :copy_from => 3,
1979 1984 :issue => {:project_id => '1', :tracker_id => '3', :status_id => '1', :subject => 'Copy with attachments'},
1980 1985 :copy_attachments => '1',
1981 1986 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain'), 'description' => 'test file'}}
1982 1987 end
1983 1988 end
1984 1989 end
1985 1990 copy = Issue.first(:order => 'id DESC')
1986 1991 assert_equal count + 1, copy.attachments.count
1987 1992 end
1988 1993
1989 1994 def test_create_as_copy_with_failure
1990 1995 @request.session[:user_id] = 2
1991 1996 post :create, :project_id => 1, :copy_from => 1,
1992 1997 :issue => {:project_id => '2', :tracker_id => '3', :status_id => '1', :subject => ''}
1993 1998
1994 1999 assert_response :success
1995 2000 assert_template 'new'
1996 2001
1997 2002 assert_not_nil assigns(:issue)
1998 2003 assert assigns(:issue).copy?
1999 2004
2000 2005 assert_tag 'form', :attributes => {:id => 'issue-form', :action => '/projects/ecookbook/issues'}
2001 2006 assert_tag 'select', :attributes => {:name => 'issue[project_id]'}
2002 2007 assert_tag 'select', :attributes => {:name => 'issue[project_id]'},
2003 2008 :child => {:tag => 'option', :attributes => {:value => '1', :selected => nil}, :content => 'eCookbook'}
2004 2009 assert_tag 'select', :attributes => {:name => 'issue[project_id]'},
2005 2010 :child => {:tag => 'option', :attributes => {:value => '2', :selected => 'selected'}, :content => 'OnlineStore'}
2006 2011 assert_tag 'input', :attributes => {:name => 'copy_from', :value => '1'}
2007 2012 end
2008 2013
2009 2014 def test_create_as_copy_on_project_without_permission_should_ignore_target_project
2010 2015 @request.session[:user_id] = 2
2011 2016 assert !User.find(2).member_of?(Project.find(4))
2012 2017
2013 2018 assert_difference 'Issue.count' do
2014 2019 post :create, :project_id => 1, :copy_from => 1,
2015 2020 :issue => {:project_id => '4', :tracker_id => '3', :status_id => '1', :subject => 'Copy'}
2016 2021 end
2017 2022 issue = Issue.first(:order => 'id DESC')
2018 2023 assert_equal 1, issue.project_id
2019 2024 end
2020 2025
2021 2026 def test_get_edit
2022 2027 @request.session[:user_id] = 2
2023 2028 get :edit, :id => 1
2024 2029 assert_response :success
2025 2030 assert_template 'edit'
2026 2031 assert_not_nil assigns(:issue)
2027 2032 assert_equal Issue.find(1), assigns(:issue)
2028 2033
2029 2034 # Be sure we don't display inactive IssuePriorities
2030 2035 assert ! IssuePriority.find(15).active?
2031 2036 assert_no_tag :option, :attributes => {:value => '15'},
2032 2037 :parent => {:tag => 'select', :attributes => {:id => 'issue_priority_id'} }
2033 2038 end
2034 2039
2035 2040 def test_get_edit_should_display_the_time_entry_form_with_log_time_permission
2036 2041 @request.session[:user_id] = 2
2037 2042 Role.find_by_name('Manager').update_attribute :permissions, [:view_issues, :edit_issues, :log_time]
2038 2043
2039 2044 get :edit, :id => 1
2040 2045 assert_tag 'input', :attributes => {:name => 'time_entry[hours]'}
2041 2046 end
2042 2047
2043 2048 def test_get_edit_should_not_display_the_time_entry_form_without_log_time_permission
2044 2049 @request.session[:user_id] = 2
2045 2050 Role.find_by_name('Manager').remove_permission! :log_time
2046 2051
2047 2052 get :edit, :id => 1
2048 2053 assert_no_tag 'input', :attributes => {:name => 'time_entry[hours]'}
2049 2054 end
2050 2055
2051 2056 def test_get_edit_with_params
2052 2057 @request.session[:user_id] = 2
2053 2058 get :edit, :id => 1, :issue => { :status_id => 5, :priority_id => 7 },
2054 2059 :time_entry => { :hours => '2.5', :comments => 'test_get_edit_with_params', :activity_id => TimeEntryActivity.first.id }
2055 2060 assert_response :success
2056 2061 assert_template 'edit'
2057 2062
2058 2063 issue = assigns(:issue)
2059 2064 assert_not_nil issue
2060 2065
2061 2066 assert_equal 5, issue.status_id
2062 2067 assert_tag :select, :attributes => { :name => 'issue[status_id]' },
2063 2068 :child => { :tag => 'option',
2064 2069 :content => 'Closed',
2065 2070 :attributes => { :selected => 'selected' } }
2066 2071
2067 2072 assert_equal 7, issue.priority_id
2068 2073 assert_tag :select, :attributes => { :name => 'issue[priority_id]' },
2069 2074 :child => { :tag => 'option',
2070 2075 :content => 'Urgent',
2071 2076 :attributes => { :selected => 'selected' } }
2072 2077
2073 2078 assert_tag :input, :attributes => { :name => 'time_entry[hours]', :value => '2.5' }
2074 2079 assert_tag :select, :attributes => { :name => 'time_entry[activity_id]' },
2075 2080 :child => { :tag => 'option',
2076 2081 :attributes => { :selected => 'selected', :value => TimeEntryActivity.first.id } }
2077 2082 assert_tag :input, :attributes => { :name => 'time_entry[comments]', :value => 'test_get_edit_with_params' }
2078 2083 end
2079 2084
2080 2085 def test_get_edit_with_multi_custom_field
2081 2086 field = CustomField.find(1)
2082 2087 field.update_attribute :multiple, true
2083 2088 issue = Issue.find(1)
2084 2089 issue.custom_field_values = {1 => ['MySQL', 'Oracle']}
2085 2090 issue.save!
2086 2091
2087 2092 @request.session[:user_id] = 2
2088 2093 get :edit, :id => 1
2089 2094 assert_response :success
2090 2095 assert_template 'edit'
2091 2096
2092 2097 assert_tag 'select', :attributes => {:name => 'issue[custom_field_values][1][]', :multiple => 'multiple'}
2093 2098 assert_tag 'select', :attributes => {:name => 'issue[custom_field_values][1][]'},
2094 2099 :child => {:tag => 'option', :attributes => {:value => 'MySQL', :selected => 'selected'}}
2095 2100 assert_tag 'select', :attributes => {:name => 'issue[custom_field_values][1][]'},
2096 2101 :child => {:tag => 'option', :attributes => {:value => 'PostgreSQL', :selected => nil}}
2097 2102 assert_tag 'select', :attributes => {:name => 'issue[custom_field_values][1][]'},
2098 2103 :child => {:tag => 'option', :attributes => {:value => 'Oracle', :selected => 'selected'}}
2099 2104 end
2100 2105
2101 2106 def test_update_edit_form
2102 2107 @request.session[:user_id] = 2
2103 2108 xhr :put, :new, :project_id => 1,
2104 2109 :id => 1,
2105 2110 :issue => {:tracker_id => 2,
2106 2111 :subject => 'This is the test_new issue',
2107 2112 :description => 'This is the description',
2108 2113 :priority_id => 5}
2109 2114 assert_response :success
2110 2115 assert_template 'attributes'
2111 2116
2112 2117 issue = assigns(:issue)
2113 2118 assert_kind_of Issue, issue
2114 2119 assert_equal 1, issue.id
2115 2120 assert_equal 1, issue.project_id
2116 2121 assert_equal 2, issue.tracker_id
2117 2122 assert_equal 'This is the test_new issue', issue.subject
2118 2123 end
2119 2124
2120 2125 def test_update_edit_form_with_project_change
2121 2126 @request.session[:user_id] = 2
2122 2127 xhr :put, :new, :project_id => 1,
2123 2128 :id => 1,
2124 2129 :project_change => '1',
2125 2130 :issue => {:project_id => 2,
2126 2131 :tracker_id => 2,
2127 2132 :subject => 'This is the test_new issue',
2128 2133 :description => 'This is the description',
2129 2134 :priority_id => 5}
2130 2135 assert_response :success
2131 2136 assert_template 'form'
2132 2137
2133 2138 issue = assigns(:issue)
2134 2139 assert_kind_of Issue, issue
2135 2140 assert_equal 1, issue.id
2136 2141 assert_equal 2, issue.project_id
2137 2142 assert_equal 2, issue.tracker_id
2138 2143 assert_equal 'This is the test_new issue', issue.subject
2139 2144 end
2140 2145
2141 2146 def test_put_update_without_custom_fields_param
2142 2147 @request.session[:user_id] = 2
2143 2148 ActionMailer::Base.deliveries.clear
2144 2149
2145 2150 issue = Issue.find(1)
2146 2151 assert_equal '125', issue.custom_value_for(2).value
2147 2152 old_subject = issue.subject
2148 2153 new_subject = 'Subject modified by IssuesControllerTest#test_post_edit'
2149 2154
2150 2155 assert_difference('Journal.count') do
2151 2156 assert_difference('JournalDetail.count', 2) do
2152 2157 put :update, :id => 1, :issue => {:subject => new_subject,
2153 2158 :priority_id => '6',
2154 2159 :category_id => '1' # no change
2155 2160 }
2156 2161 end
2157 2162 end
2158 2163 assert_redirected_to :action => 'show', :id => '1'
2159 2164 issue.reload
2160 2165 assert_equal new_subject, issue.subject
2161 2166 # Make sure custom fields were not cleared
2162 2167 assert_equal '125', issue.custom_value_for(2).value
2163 2168
2164 2169 mail = ActionMailer::Base.deliveries.last
2165 2170 assert_not_nil mail
2166 2171 assert mail.subject.starts_with?("[#{issue.project.name} - #{issue.tracker.name} ##{issue.id}]")
2167 2172 assert_mail_body_match "Subject changed from #{old_subject} to #{new_subject}", mail
2168 2173 end
2169 2174
2170 2175 def test_put_update_with_project_change
2171 2176 @request.session[:user_id] = 2
2172 2177 ActionMailer::Base.deliveries.clear
2173 2178
2174 2179 assert_difference('Journal.count') do
2175 2180 assert_difference('JournalDetail.count', 3) do
2176 2181 put :update, :id => 1, :issue => {:project_id => '2',
2177 2182 :tracker_id => '1', # no change
2178 2183 :priority_id => '6',
2179 2184 :category_id => '3'
2180 2185 }
2181 2186 end
2182 2187 end
2183 2188 assert_redirected_to :action => 'show', :id => '1'
2184 2189 issue = Issue.find(1)
2185 2190 assert_equal 2, issue.project_id
2186 2191 assert_equal 1, issue.tracker_id
2187 2192 assert_equal 6, issue.priority_id
2188 2193 assert_equal 3, issue.category_id
2189 2194
2190 2195 mail = ActionMailer::Base.deliveries.last
2191 2196 assert_not_nil mail
2192 2197 assert mail.subject.starts_with?("[#{issue.project.name} - #{issue.tracker.name} ##{issue.id}]")
2193 2198 assert_mail_body_match "Project changed from eCookbook to OnlineStore", mail
2194 2199 end
2195 2200
2196 2201 def test_put_update_with_tracker_change
2197 2202 @request.session[:user_id] = 2
2198 2203 ActionMailer::Base.deliveries.clear
2199 2204
2200 2205 assert_difference('Journal.count') do
2201 2206 assert_difference('JournalDetail.count', 2) do
2202 2207 put :update, :id => 1, :issue => {:project_id => '1',
2203 2208 :tracker_id => '2',
2204 2209 :priority_id => '6'
2205 2210 }
2206 2211 end
2207 2212 end
2208 2213 assert_redirected_to :action => 'show', :id => '1'
2209 2214 issue = Issue.find(1)
2210 2215 assert_equal 1, issue.project_id
2211 2216 assert_equal 2, issue.tracker_id
2212 2217 assert_equal 6, issue.priority_id
2213 2218 assert_equal 1, issue.category_id
2214 2219
2215 2220 mail = ActionMailer::Base.deliveries.last
2216 2221 assert_not_nil mail
2217 2222 assert mail.subject.starts_with?("[#{issue.project.name} - #{issue.tracker.name} ##{issue.id}]")
2218 2223 assert_mail_body_match "Tracker changed from Bug to Feature request", mail
2219 2224 end
2220 2225
2221 2226 def test_put_update_with_custom_field_change
2222 2227 @request.session[:user_id] = 2
2223 2228 issue = Issue.find(1)
2224 2229 assert_equal '125', issue.custom_value_for(2).value
2225 2230
2226 2231 assert_difference('Journal.count') do
2227 2232 assert_difference('JournalDetail.count', 3) do
2228 2233 put :update, :id => 1, :issue => {:subject => 'Custom field change',
2229 2234 :priority_id => '6',
2230 2235 :category_id => '1', # no change
2231 2236 :custom_field_values => { '2' => 'New custom value' }
2232 2237 }
2233 2238 end
2234 2239 end
2235 2240 assert_redirected_to :action => 'show', :id => '1'
2236 2241 issue.reload
2237 2242 assert_equal 'New custom value', issue.custom_value_for(2).value
2238 2243
2239 2244 mail = ActionMailer::Base.deliveries.last
2240 2245 assert_not_nil mail
2241 2246 assert_mail_body_match "Searchable field changed from 125 to New custom value", mail
2242 2247 end
2243 2248
2244 2249 def test_put_update_with_multi_custom_field_change
2245 2250 field = CustomField.find(1)
2246 2251 field.update_attribute :multiple, true
2247 2252 issue = Issue.find(1)
2248 2253 issue.custom_field_values = {1 => ['MySQL', 'Oracle']}
2249 2254 issue.save!
2250 2255
2251 2256 @request.session[:user_id] = 2
2252 2257 assert_difference('Journal.count') do
2253 2258 assert_difference('JournalDetail.count', 3) do
2254 2259 put :update, :id => 1,
2255 2260 :issue => {
2256 2261 :subject => 'Custom field change',
2257 2262 :custom_field_values => { '1' => ['', 'Oracle', 'PostgreSQL'] }
2258 2263 }
2259 2264 end
2260 2265 end
2261 2266 assert_redirected_to :action => 'show', :id => '1'
2262 2267 assert_equal ['Oracle', 'PostgreSQL'], Issue.find(1).custom_field_value(1).sort
2263 2268 end
2264 2269
2265 2270 def test_put_update_with_status_and_assignee_change
2266 2271 issue = Issue.find(1)
2267 2272 assert_equal 1, issue.status_id
2268 2273 @request.session[:user_id] = 2
2269 2274 assert_difference('TimeEntry.count', 0) do
2270 2275 put :update,
2271 2276 :id => 1,
2272 2277 :issue => { :status_id => 2, :assigned_to_id => 3 },
2273 2278 :notes => 'Assigned to dlopper',
2274 2279 :time_entry => { :hours => '', :comments => '', :activity_id => TimeEntryActivity.first }
2275 2280 end
2276 2281 assert_redirected_to :action => 'show', :id => '1'
2277 2282 issue.reload
2278 2283 assert_equal 2, issue.status_id
2279 2284 j = Journal.find(:first, :order => 'id DESC')
2280 2285 assert_equal 'Assigned to dlopper', j.notes
2281 2286 assert_equal 2, j.details.size
2282 2287
2283 2288 mail = ActionMailer::Base.deliveries.last
2284 2289 assert_mail_body_match "Status changed from New to Assigned", mail
2285 2290 # subject should contain the new status
2286 2291 assert mail.subject.include?("(#{ IssueStatus.find(2).name })")
2287 2292 end
2288 2293
2289 2294 def test_put_update_with_note_only
2290 2295 notes = 'Note added by IssuesControllerTest#test_update_with_note_only'
2291 2296 # anonymous user
2292 2297 put :update,
2293 2298 :id => 1,
2294 2299 :notes => notes
2295 2300 assert_redirected_to :action => 'show', :id => '1'
2296 2301 j = Journal.find(:first, :order => 'id DESC')
2297 2302 assert_equal notes, j.notes
2298 2303 assert_equal 0, j.details.size
2299 2304 assert_equal User.anonymous, j.user
2300 2305
2301 2306 mail = ActionMailer::Base.deliveries.last
2302 2307 assert_mail_body_match notes, mail
2303 2308 end
2304 2309
2305 2310 def test_put_update_with_note_and_spent_time
2306 2311 @request.session[:user_id] = 2
2307 2312 spent_hours_before = Issue.find(1).spent_hours
2308 2313 assert_difference('TimeEntry.count') do
2309 2314 put :update,
2310 2315 :id => 1,
2311 2316 :notes => '2.5 hours added',
2312 2317 :time_entry => { :hours => '2.5', :comments => 'test_put_update_with_note_and_spent_time', :activity_id => TimeEntryActivity.first.id }
2313 2318 end
2314 2319 assert_redirected_to :action => 'show', :id => '1'
2315 2320
2316 2321 issue = Issue.find(1)
2317 2322
2318 2323 j = Journal.find(:first, :order => 'id DESC')
2319 2324 assert_equal '2.5 hours added', j.notes
2320 2325 assert_equal 0, j.details.size
2321 2326
2322 2327 t = issue.time_entries.find_by_comments('test_put_update_with_note_and_spent_time')
2323 2328 assert_not_nil t
2324 2329 assert_equal 2.5, t.hours
2325 2330 assert_equal spent_hours_before + 2.5, issue.spent_hours
2326 2331 end
2327 2332
2328 2333 def test_put_update_with_attachment_only
2329 2334 set_tmp_attachments_directory
2330 2335
2331 2336 # Delete all fixtured journals, a race condition can occur causing the wrong
2332 2337 # journal to get fetched in the next find.
2333 2338 Journal.delete_all
2334 2339
2335 2340 # anonymous user
2336 2341 assert_difference 'Attachment.count' do
2337 2342 put :update, :id => 1,
2338 2343 :notes => '',
2339 2344 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain'), 'description' => 'test file'}}
2340 2345 end
2341 2346
2342 2347 assert_redirected_to :action => 'show', :id => '1'
2343 2348 j = Issue.find(1).journals.find(:first, :order => 'id DESC')
2344 2349 assert j.notes.blank?
2345 2350 assert_equal 1, j.details.size
2346 2351 assert_equal 'testfile.txt', j.details.first.value
2347 2352 assert_equal User.anonymous, j.user
2348 2353
2349 2354 attachment = Attachment.first(:order => 'id DESC')
2350 2355 assert_equal Issue.find(1), attachment.container
2351 2356 assert_equal User.anonymous, attachment.author
2352 2357 assert_equal 'testfile.txt', attachment.filename
2353 2358 assert_equal 'text/plain', attachment.content_type
2354 2359 assert_equal 'test file', attachment.description
2355 2360 assert_equal 59, attachment.filesize
2356 2361 assert File.exists?(attachment.diskfile)
2357 2362 assert_equal 59, File.size(attachment.diskfile)
2358 2363
2359 2364 mail = ActionMailer::Base.deliveries.last
2360 2365 assert_mail_body_match 'testfile.txt', mail
2361 2366 end
2362 2367
2363 2368 def test_put_update_with_failure_should_save_attachments
2364 2369 set_tmp_attachments_directory
2365 2370 @request.session[:user_id] = 2
2366 2371
2367 2372 assert_no_difference 'Journal.count' do
2368 2373 assert_difference 'Attachment.count' do
2369 2374 put :update, :id => 1,
2370 2375 :issue => { :subject => '' },
2371 2376 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain'), 'description' => 'test file'}}
2372 2377 assert_response :success
2373 2378 assert_template 'edit'
2374 2379 end
2375 2380 end
2376 2381
2377 2382 attachment = Attachment.first(:order => 'id DESC')
2378 2383 assert_equal 'testfile.txt', attachment.filename
2379 2384 assert File.exists?(attachment.diskfile)
2380 2385 assert_nil attachment.container
2381 2386
2382 2387 assert_tag 'input', :attributes => {:name => 'attachments[p0][token]', :value => attachment.token}
2383 2388 assert_tag 'span', :content => /testfile.txt/
2384 2389 end
2385 2390
2386 2391 def test_put_update_with_failure_should_keep_saved_attachments
2387 2392 set_tmp_attachments_directory
2388 2393 attachment = Attachment.create!(:file => uploaded_test_file("testfile.txt", "text/plain"), :author_id => 2)
2389 2394 @request.session[:user_id] = 2
2390 2395
2391 2396 assert_no_difference 'Journal.count' do
2392 2397 assert_no_difference 'Attachment.count' do
2393 2398 put :update, :id => 1,
2394 2399 :issue => { :subject => '' },
2395 2400 :attachments => {'p0' => {'token' => attachment.token}}
2396 2401 assert_response :success
2397 2402 assert_template 'edit'
2398 2403 end
2399 2404 end
2400 2405
2401 2406 assert_tag 'input', :attributes => {:name => 'attachments[p0][token]', :value => attachment.token}
2402 2407 assert_tag 'span', :content => /testfile.txt/
2403 2408 end
2404 2409
2405 2410 def test_put_update_should_attach_saved_attachments
2406 2411 set_tmp_attachments_directory
2407 2412 attachment = Attachment.create!(:file => uploaded_test_file("testfile.txt", "text/plain"), :author_id => 2)
2408 2413 @request.session[:user_id] = 2
2409 2414
2410 2415 assert_difference 'Journal.count' do
2411 2416 assert_difference 'JournalDetail.count' do
2412 2417 assert_no_difference 'Attachment.count' do
2413 2418 put :update, :id => 1,
2414 2419 :notes => 'Attachment added',
2415 2420 :attachments => {'p0' => {'token' => attachment.token}}
2416 2421 assert_redirected_to '/issues/1'
2417 2422 end
2418 2423 end
2419 2424 end
2420 2425
2421 2426 attachment.reload
2422 2427 assert_equal Issue.find(1), attachment.container
2423 2428
2424 2429 journal = Journal.first(:order => 'id DESC')
2425 2430 assert_equal 1, journal.details.size
2426 2431 assert_equal 'testfile.txt', journal.details.first.value
2427 2432 end
2428 2433
2429 2434 def test_put_update_with_attachment_that_fails_to_save
2430 2435 set_tmp_attachments_directory
2431 2436
2432 2437 # Delete all fixtured journals, a race condition can occur causing the wrong
2433 2438 # journal to get fetched in the next find.
2434 2439 Journal.delete_all
2435 2440
2436 2441 # Mock out the unsaved attachment
2437 2442 Attachment.any_instance.stubs(:create).returns(Attachment.new)
2438 2443
2439 2444 # anonymous user
2440 2445 put :update,
2441 2446 :id => 1,
2442 2447 :notes => '',
2443 2448 :attachments => {'1' => {'file' => uploaded_test_file('testfile.txt', 'text/plain')}}
2444 2449 assert_redirected_to :action => 'show', :id => '1'
2445 2450 assert_equal '1 file(s) could not be saved.', flash[:warning]
2446 2451 end
2447 2452
2448 2453 def test_put_update_with_no_change
2449 2454 issue = Issue.find(1)
2450 2455 issue.journals.clear
2451 2456 ActionMailer::Base.deliveries.clear
2452 2457
2453 2458 put :update,
2454 2459 :id => 1,
2455 2460 :notes => ''
2456 2461 assert_redirected_to :action => 'show', :id => '1'
2457 2462
2458 2463 issue.reload
2459 2464 assert issue.journals.empty?
2460 2465 # No email should be sent
2461 2466 assert ActionMailer::Base.deliveries.empty?
2462 2467 end
2463 2468
2464 2469 def test_put_update_should_send_a_notification
2465 2470 @request.session[:user_id] = 2
2466 2471 ActionMailer::Base.deliveries.clear
2467 2472 issue = Issue.find(1)
2468 2473 old_subject = issue.subject
2469 2474 new_subject = 'Subject modified by IssuesControllerTest#test_post_edit'
2470 2475
2471 2476 put :update, :id => 1, :issue => {:subject => new_subject,
2472 2477 :priority_id => '6',
2473 2478 :category_id => '1' # no change
2474 2479 }
2475 2480 assert_equal 1, ActionMailer::Base.deliveries.size
2476 2481 end
2477 2482
2478 2483 def test_put_update_with_invalid_spent_time_hours_only
2479 2484 @request.session[:user_id] = 2
2480 2485 notes = 'Note added by IssuesControllerTest#test_post_edit_with_invalid_spent_time'
2481 2486
2482 2487 assert_no_difference('Journal.count') do
2483 2488 put :update,
2484 2489 :id => 1,
2485 2490 :notes => notes,
2486 2491 :time_entry => {"comments"=>"", "activity_id"=>"", "hours"=>"2z"}
2487 2492 end
2488 2493 assert_response :success
2489 2494 assert_template 'edit'
2490 2495
2491 2496 assert_error_tag :descendant => {:content => /Activity can't be blank/}
2492 2497 assert_tag :textarea, :attributes => { :name => 'notes' }, :content => notes
2493 2498 assert_tag :input, :attributes => { :name => 'time_entry[hours]', :value => "2z" }
2494 2499 end
2495 2500
2496 2501 def test_put_update_with_invalid_spent_time_comments_only
2497 2502 @request.session[:user_id] = 2
2498 2503 notes = 'Note added by IssuesControllerTest#test_post_edit_with_invalid_spent_time'
2499 2504
2500 2505 assert_no_difference('Journal.count') do
2501 2506 put :update,
2502 2507 :id => 1,
2503 2508 :notes => notes,
2504 2509 :time_entry => {"comments"=>"this is my comment", "activity_id"=>"", "hours"=>""}
2505 2510 end
2506 2511 assert_response :success
2507 2512 assert_template 'edit'
2508 2513
2509 2514 assert_error_tag :descendant => {:content => /Activity can't be blank/}
2510 2515 assert_error_tag :descendant => {:content => /Hours can't be blank/}
2511 2516 assert_tag :textarea, :attributes => { :name => 'notes' }, :content => notes
2512 2517 assert_tag :input, :attributes => { :name => 'time_entry[comments]', :value => "this is my comment" }
2513 2518 end
2514 2519
2515 2520 def test_put_update_should_allow_fixed_version_to_be_set_to_a_subproject
2516 2521 issue = Issue.find(2)
2517 2522 @request.session[:user_id] = 2
2518 2523
2519 2524 put :update,
2520 2525 :id => issue.id,
2521 2526 :issue => {
2522 2527 :fixed_version_id => 4
2523 2528 }
2524 2529
2525 2530 assert_response :redirect
2526 2531 issue.reload
2527 2532 assert_equal 4, issue.fixed_version_id
2528 2533 assert_not_equal issue.project_id, issue.fixed_version.project_id
2529 2534 end
2530 2535
2531 2536 def test_put_update_should_redirect_back_using_the_back_url_parameter
2532 2537 issue = Issue.find(2)
2533 2538 @request.session[:user_id] = 2
2534 2539
2535 2540 put :update,
2536 2541 :id => issue.id,
2537 2542 :issue => {
2538 2543 :fixed_version_id => 4
2539 2544 },
2540 2545 :back_url => '/issues'
2541 2546
2542 2547 assert_response :redirect
2543 2548 assert_redirected_to '/issues'
2544 2549 end
2545 2550
2546 2551 def test_put_update_should_not_redirect_back_using_the_back_url_parameter_off_the_host
2547 2552 issue = Issue.find(2)
2548 2553 @request.session[:user_id] = 2
2549 2554
2550 2555 put :update,
2551 2556 :id => issue.id,
2552 2557 :issue => {
2553 2558 :fixed_version_id => 4
2554 2559 },
2555 2560 :back_url => 'http://google.com'
2556 2561
2557 2562 assert_response :redirect
2558 2563 assert_redirected_to :controller => 'issues', :action => 'show', :id => issue.id
2559 2564 end
2560 2565
2561 2566 def test_get_bulk_edit
2562 2567 @request.session[:user_id] = 2
2563 2568 get :bulk_edit, :ids => [1, 2]
2564 2569 assert_response :success
2565 2570 assert_template 'bulk_edit'
2566 2571
2567 2572 assert_tag :select, :attributes => {:name => 'issue[project_id]'}
2568 2573 assert_tag :input, :attributes => {:name => 'issue[parent_issue_id]'}
2569 2574
2570 2575 # Project specific custom field, date type
2571 2576 field = CustomField.find(9)
2572 2577 assert !field.is_for_all?
2573 2578 assert_equal 'date', field.field_format
2574 2579 assert_tag :input, :attributes => {:name => 'issue[custom_field_values][9]'}
2575 2580
2576 2581 # System wide custom field
2577 2582 assert CustomField.find(1).is_for_all?
2578 2583 assert_tag :select, :attributes => {:name => 'issue[custom_field_values][1]'}
2579 2584
2580 2585 # Be sure we don't display inactive IssuePriorities
2581 2586 assert ! IssuePriority.find(15).active?
2582 2587 assert_no_tag :option, :attributes => {:value => '15'},
2583 2588 :parent => {:tag => 'select', :attributes => {:id => 'issue_priority_id'} }
2584 2589 end
2585 2590
2586 2591 def test_get_bulk_edit_on_different_projects
2587 2592 @request.session[:user_id] = 2
2588 2593 get :bulk_edit, :ids => [1, 2, 6]
2589 2594 assert_response :success
2590 2595 assert_template 'bulk_edit'
2591 2596
2592 2597 # Can not set issues from different projects as children of an issue
2593 2598 assert_no_tag :input, :attributes => {:name => 'issue[parent_issue_id]'}
2594 2599
2595 2600 # Project specific custom field, date type
2596 2601 field = CustomField.find(9)
2597 2602 assert !field.is_for_all?
2598 2603 assert !field.project_ids.include?(Issue.find(6).project_id)
2599 2604 assert_no_tag :input, :attributes => {:name => 'issue[custom_field_values][9]'}
2600 2605 end
2601 2606
2602 2607 def test_get_bulk_edit_with_user_custom_field
2603 2608 field = IssueCustomField.create!(:name => 'Tester', :field_format => 'user', :is_for_all => true)
2604 2609
2605 2610 @request.session[:user_id] = 2
2606 2611 get :bulk_edit, :ids => [1, 2]
2607 2612 assert_response :success
2608 2613 assert_template 'bulk_edit'
2609 2614
2610 2615 assert_tag :select,
2611 2616 :attributes => {:name => "issue[custom_field_values][#{field.id}]"},
2612 2617 :children => {
2613 2618 :only => {:tag => 'option'},
2614 2619 :count => Project.find(1).users.count + 1
2615 2620 }
2616 2621 end
2617 2622
2618 2623 def test_get_bulk_edit_with_version_custom_field
2619 2624 field = IssueCustomField.create!(:name => 'Affected version', :field_format => 'version', :is_for_all => true)
2620 2625
2621 2626 @request.session[:user_id] = 2
2622 2627 get :bulk_edit, :ids => [1, 2]
2623 2628 assert_response :success
2624 2629 assert_template 'bulk_edit'
2625 2630
2626 2631 assert_tag :select,
2627 2632 :attributes => {:name => "issue[custom_field_values][#{field.id}]"},
2628 2633 :children => {
2629 2634 :only => {:tag => 'option'},
2630 2635 :count => Project.find(1).shared_versions.count + 1
2631 2636 }
2632 2637 end
2633 2638
2634 2639 def test_get_bulk_edit_with_multi_custom_field
2635 2640 field = CustomField.find(1)
2636 2641 field.update_attribute :multiple, true
2637 2642
2638 2643 @request.session[:user_id] = 2
2639 2644 get :bulk_edit, :ids => [1, 2]
2640 2645 assert_response :success
2641 2646 assert_template 'bulk_edit'
2642 2647
2643 2648 assert_tag :select,
2644 2649 :attributes => {:name => "issue[custom_field_values][1][]"},
2645 2650 :children => {
2646 2651 :only => {:tag => 'option'},
2647 2652 :count => 3
2648 2653 }
2649 2654 end
2650 2655
2651 2656 def test_bulk_edit_should_only_propose_statuses_allowed_for_all_issues
2652 2657 Workflow.delete_all
2653 2658 Workflow.create!(:role_id => 1, :tracker_id => 1, :old_status_id => 1, :new_status_id => 1)
2654 2659 Workflow.create!(:role_id => 1, :tracker_id => 1, :old_status_id => 1, :new_status_id => 3)
2655 2660 Workflow.create!(:role_id => 1, :tracker_id => 1, :old_status_id => 1, :new_status_id => 4)
2656 2661 Workflow.create!(:role_id => 1, :tracker_id => 2, :old_status_id => 2, :new_status_id => 1)
2657 2662 Workflow.create!(:role_id => 1, :tracker_id => 2, :old_status_id => 2, :new_status_id => 3)
2658 2663 Workflow.create!(:role_id => 1, :tracker_id => 2, :old_status_id => 2, :new_status_id => 5)
2659 2664 @request.session[:user_id] = 2
2660 2665 get :bulk_edit, :ids => [1, 2]
2661 2666
2662 2667 assert_response :success
2663 2668 statuses = assigns(:available_statuses)
2664 2669 assert_not_nil statuses
2665 2670 assert_equal [1, 3], statuses.map(&:id).sort
2666 2671
2667 2672 assert_tag 'select', :attributes => {:name => 'issue[status_id]'},
2668 2673 :children => {:count => 3} # 2 statuses + "no change" option
2669 2674 end
2670 2675
2671 2676 def test_bulk_edit_should_propose_target_project_open_shared_versions
2672 2677 @request.session[:user_id] = 2
2673 2678 post :bulk_edit, :ids => [1, 2, 6], :issue => {:project_id => 1}
2674 2679 assert_response :success
2675 2680 assert_template 'bulk_edit'
2676 2681 assert_equal Project.find(1).shared_versions.open.all.sort, assigns(:versions).sort
2677 2682 assert_tag 'select',
2678 2683 :attributes => {:name => 'issue[fixed_version_id]'},
2679 2684 :descendant => {:tag => 'option', :content => '2.0'}
2680 2685 end
2681 2686
2682 2687 def test_bulk_edit_should_propose_target_project_categories
2683 2688 @request.session[:user_id] = 2
2684 2689 post :bulk_edit, :ids => [1, 2, 6], :issue => {:project_id => 1}
2685 2690 assert_response :success
2686 2691 assert_template 'bulk_edit'
2687 2692 assert_equal Project.find(1).issue_categories.sort, assigns(:categories).sort
2688 2693 assert_tag 'select',
2689 2694 :attributes => {:name => 'issue[category_id]'},
2690 2695 :descendant => {:tag => 'option', :content => 'Recipes'}
2691 2696 end
2692 2697
2693 2698 def test_bulk_update
2694 2699 @request.session[:user_id] = 2
2695 2700 # update issues priority
2696 2701 post :bulk_update, :ids => [1, 2], :notes => 'Bulk editing',
2697 2702 :issue => {:priority_id => 7,
2698 2703 :assigned_to_id => '',
2699 2704 :custom_field_values => {'2' => ''}}
2700 2705
2701 2706 assert_response 302
2702 2707 # check that the issues were updated
2703 2708 assert_equal [7, 7], Issue.find_all_by_id([1, 2]).collect {|i| i.priority.id}
2704 2709
2705 2710 issue = Issue.find(1)
2706 2711 journal = issue.journals.find(:first, :order => 'created_on DESC')
2707 2712 assert_equal '125', issue.custom_value_for(2).value
2708 2713 assert_equal 'Bulk editing', journal.notes
2709 2714 assert_equal 1, journal.details.size
2710 2715 end
2711 2716
2712 2717 def test_bulk_update_with_group_assignee
2713 2718 group = Group.find(11)
2714 2719 project = Project.find(1)
2715 2720 project.members << Member.new(:principal => group, :roles => [Role.givable.first])
2716 2721
2717 2722 @request.session[:user_id] = 2
2718 2723 # update issues assignee
2719 2724 post :bulk_update, :ids => [1, 2], :notes => 'Bulk editing',
2720 2725 :issue => {:priority_id => '',
2721 2726 :assigned_to_id => group.id,
2722 2727 :custom_field_values => {'2' => ''}}
2723 2728
2724 2729 assert_response 302
2725 2730 assert_equal [group, group], Issue.find_all_by_id([1, 2]).collect {|i| i.assigned_to}
2726 2731 end
2727 2732
2728 2733 def test_bulk_update_on_different_projects
2729 2734 @request.session[:user_id] = 2
2730 2735 # update issues priority
2731 2736 post :bulk_update, :ids => [1, 2, 6], :notes => 'Bulk editing',
2732 2737 :issue => {:priority_id => 7,
2733 2738 :assigned_to_id => '',
2734 2739 :custom_field_values => {'2' => ''}}
2735 2740
2736 2741 assert_response 302
2737 2742 # check that the issues were updated
2738 2743 assert_equal [7, 7, 7], Issue.find([1,2,6]).map(&:priority_id)
2739 2744
2740 2745 issue = Issue.find(1)
2741 2746 journal = issue.journals.find(:first, :order => 'created_on DESC')
2742 2747 assert_equal '125', issue.custom_value_for(2).value
2743 2748 assert_equal 'Bulk editing', journal.notes
2744 2749 assert_equal 1, journal.details.size
2745 2750 end
2746 2751
2747 2752 def test_bulk_update_on_different_projects_without_rights
2748 2753 @request.session[:user_id] = 3
2749 2754 user = User.find(3)
2750 2755 action = { :controller => "issues", :action => "bulk_update" }
2751 2756 assert user.allowed_to?(action, Issue.find(1).project)
2752 2757 assert ! user.allowed_to?(action, Issue.find(6).project)
2753 2758 post :bulk_update, :ids => [1, 6], :notes => 'Bulk should fail',
2754 2759 :issue => {:priority_id => 7,
2755 2760 :assigned_to_id => '',
2756 2761 :custom_field_values => {'2' => ''}}
2757 2762 assert_response 403
2758 2763 assert_not_equal "Bulk should fail", Journal.last.notes
2759 2764 end
2760 2765
2761 2766 def test_bullk_update_should_send_a_notification
2762 2767 @request.session[:user_id] = 2
2763 2768 ActionMailer::Base.deliveries.clear
2764 2769 post(:bulk_update,
2765 2770 {
2766 2771 :ids => [1, 2],
2767 2772 :notes => 'Bulk editing',
2768 2773 :issue => {
2769 2774 :priority_id => 7,
2770 2775 :assigned_to_id => '',
2771 2776 :custom_field_values => {'2' => ''}
2772 2777 }
2773 2778 })
2774 2779
2775 2780 assert_response 302
2776 2781 assert_equal 2, ActionMailer::Base.deliveries.size
2777 2782 end
2778 2783
2779 2784 def test_bulk_update_project
2780 2785 @request.session[:user_id] = 2
2781 2786 post :bulk_update, :ids => [1, 2], :issue => {:project_id => '2'}
2782 2787 assert_redirected_to :controller => 'issues', :action => 'index', :project_id => 'ecookbook'
2783 2788 # Issues moved to project 2
2784 2789 assert_equal 2, Issue.find(1).project_id
2785 2790 assert_equal 2, Issue.find(2).project_id
2786 2791 # No tracker change
2787 2792 assert_equal 1, Issue.find(1).tracker_id
2788 2793 assert_equal 2, Issue.find(2).tracker_id
2789 2794 end
2790 2795
2791 2796 def test_bulk_update_project_on_single_issue_should_follow_when_needed
2792 2797 @request.session[:user_id] = 2
2793 2798 post :bulk_update, :id => 1, :issue => {:project_id => '2'}, :follow => '1'
2794 2799 assert_redirected_to '/issues/1'
2795 2800 end
2796 2801
2797 2802 def test_bulk_update_project_on_multiple_issues_should_follow_when_needed
2798 2803 @request.session[:user_id] = 2
2799 2804 post :bulk_update, :id => [1, 2], :issue => {:project_id => '2'}, :follow => '1'
2800 2805 assert_redirected_to '/projects/onlinestore/issues'
2801 2806 end
2802 2807
2803 2808 def test_bulk_update_tracker
2804 2809 @request.session[:user_id] = 2
2805 2810 post :bulk_update, :ids => [1, 2], :issue => {:tracker_id => '2'}
2806 2811 assert_redirected_to :controller => 'issues', :action => 'index', :project_id => 'ecookbook'
2807 2812 assert_equal 2, Issue.find(1).tracker_id
2808 2813 assert_equal 2, Issue.find(2).tracker_id
2809 2814 end
2810 2815
2811 2816 def test_bulk_update_status
2812 2817 @request.session[:user_id] = 2
2813 2818 # update issues priority
2814 2819 post :bulk_update, :ids => [1, 2], :notes => 'Bulk editing status',
2815 2820 :issue => {:priority_id => '',
2816 2821 :assigned_to_id => '',
2817 2822 :status_id => '5'}
2818 2823
2819 2824 assert_response 302
2820 2825 issue = Issue.find(1)
2821 2826 assert issue.closed?
2822 2827 end
2823 2828
2824 2829 def test_bulk_update_priority
2825 2830 @request.session[:user_id] = 2
2826 2831 post :bulk_update, :ids => [1, 2], :issue => {:priority_id => 6}
2827 2832
2828 2833 assert_redirected_to :controller => 'issues', :action => 'index', :project_id => 'ecookbook'
2829 2834 assert_equal 6, Issue.find(1).priority_id
2830 2835 assert_equal 6, Issue.find(2).priority_id
2831 2836 end
2832 2837
2833 2838 def test_bulk_update_with_notes
2834 2839 @request.session[:user_id] = 2
2835 2840 post :bulk_update, :ids => [1, 2], :notes => 'Moving two issues'
2836 2841
2837 2842 assert_redirected_to :controller => 'issues', :action => 'index', :project_id => 'ecookbook'
2838 2843 assert_equal 'Moving two issues', Issue.find(1).journals.sort_by(&:id).last.notes
2839 2844 assert_equal 'Moving two issues', Issue.find(2).journals.sort_by(&:id).last.notes
2840 2845 end
2841 2846
2842 2847 def test_bulk_update_parent_id
2843 2848 @request.session[:user_id] = 2
2844 2849 post :bulk_update, :ids => [1, 3],
2845 2850 :notes => 'Bulk editing parent',
2846 2851 :issue => {:priority_id => '', :assigned_to_id => '', :status_id => '', :parent_issue_id => '2'}
2847 2852
2848 2853 assert_response 302
2849 2854 parent = Issue.find(2)
2850 2855 assert_equal parent.id, Issue.find(1).parent_id
2851 2856 assert_equal parent.id, Issue.find(3).parent_id
2852 2857 assert_equal [1, 3], parent.children.collect(&:id).sort
2853 2858 end
2854 2859
2855 2860 def test_bulk_update_custom_field
2856 2861 @request.session[:user_id] = 2
2857 2862 # update issues priority
2858 2863 post :bulk_update, :ids => [1, 2], :notes => 'Bulk editing custom field',
2859 2864 :issue => {:priority_id => '',
2860 2865 :assigned_to_id => '',
2861 2866 :custom_field_values => {'2' => '777'}}
2862 2867
2863 2868 assert_response 302
2864 2869
2865 2870 issue = Issue.find(1)
2866 2871 journal = issue.journals.find(:first, :order => 'created_on DESC')
2867 2872 assert_equal '777', issue.custom_value_for(2).value
2868 2873 assert_equal 1, journal.details.size
2869 2874 assert_equal '125', journal.details.first.old_value
2870 2875 assert_equal '777', journal.details.first.value
2871 2876 end
2872 2877
2873 2878 def test_bulk_update_multi_custom_field
2874 2879 field = CustomField.find(1)
2875 2880 field.update_attribute :multiple, true
2876 2881
2877 2882 @request.session[:user_id] = 2
2878 2883 post :bulk_update, :ids => [1, 2, 3], :notes => 'Bulk editing multi custom field',
2879 2884 :issue => {:priority_id => '',
2880 2885 :assigned_to_id => '',
2881 2886 :custom_field_values => {'1' => ['MySQL', 'Oracle']}}
2882 2887
2883 2888 assert_response 302
2884 2889
2885 2890 assert_equal ['MySQL', 'Oracle'], Issue.find(1).custom_field_value(1).sort
2886 2891 assert_equal ['MySQL', 'Oracle'], Issue.find(3).custom_field_value(1).sort
2887 2892 # the custom field is not associated with the issue tracker
2888 2893 assert_nil Issue.find(2).custom_field_value(1)
2889 2894 end
2890 2895
2891 2896 def test_bulk_update_unassign
2892 2897 assert_not_nil Issue.find(2).assigned_to
2893 2898 @request.session[:user_id] = 2
2894 2899 # unassign issues
2895 2900 post :bulk_update, :ids => [1, 2], :notes => 'Bulk unassigning', :issue => {:assigned_to_id => 'none'}
2896 2901 assert_response 302
2897 2902 # check that the issues were updated
2898 2903 assert_nil Issue.find(2).assigned_to
2899 2904 end
2900 2905
2901 2906 def test_post_bulk_update_should_allow_fixed_version_to_be_set_to_a_subproject
2902 2907 @request.session[:user_id] = 2
2903 2908
2904 2909 post :bulk_update, :ids => [1,2], :issue => {:fixed_version_id => 4}
2905 2910
2906 2911 assert_response :redirect
2907 2912 issues = Issue.find([1,2])
2908 2913 issues.each do |issue|
2909 2914 assert_equal 4, issue.fixed_version_id
2910 2915 assert_not_equal issue.project_id, issue.fixed_version.project_id
2911 2916 end
2912 2917 end
2913 2918
2914 2919 def test_post_bulk_update_should_redirect_back_using_the_back_url_parameter
2915 2920 @request.session[:user_id] = 2
2916 2921 post :bulk_update, :ids => [1,2], :back_url => '/issues'
2917 2922
2918 2923 assert_response :redirect
2919 2924 assert_redirected_to '/issues'
2920 2925 end
2921 2926
2922 2927 def test_post_bulk_update_should_not_redirect_back_using_the_back_url_parameter_off_the_host
2923 2928 @request.session[:user_id] = 2
2924 2929 post :bulk_update, :ids => [1,2], :back_url => 'http://google.com'
2925 2930
2926 2931 assert_response :redirect
2927 2932 assert_redirected_to :controller => 'issues', :action => 'index', :project_id => Project.find(1).identifier
2928 2933 end
2929 2934
2930 2935 def test_bulk_copy_to_another_project
2931 2936 @request.session[:user_id] = 2
2932 2937 assert_difference 'Issue.count', 2 do
2933 2938 assert_no_difference 'Project.find(1).issues.count' do
2934 2939 post :bulk_update, :ids => [1, 2], :issue => {:project_id => '2'}, :copy => '1'
2935 2940 end
2936 2941 end
2937 2942 assert_redirected_to '/projects/ecookbook/issues'
2938 2943 end
2939 2944
2940 2945 def test_bulk_copy_should_allow_not_changing_the_issue_attributes
2941 2946 @request.session[:user_id] = 2
2942 2947 issue_before_move = Issue.find(1)
2943 2948 assert_difference 'Issue.count', 1 do
2944 2949 assert_no_difference 'Project.find(1).issues.count' do
2945 2950 post :bulk_update, :ids => [1], :copy => '1',
2946 2951 :issue => {
2947 2952 :project_id => '2', :tracker_id => '', :assigned_to_id => '',
2948 2953 :status_id => '', :start_date => '', :due_date => ''
2949 2954 }
2950 2955 end
2951 2956 end
2952 2957 issue_after_move = Issue.first(:order => 'id desc', :conditions => {:project_id => 2})
2953 2958 assert_equal issue_before_move.tracker_id, issue_after_move.tracker_id
2954 2959 assert_equal issue_before_move.status_id, issue_after_move.status_id
2955 2960 assert_equal issue_before_move.assigned_to_id, issue_after_move.assigned_to_id
2956 2961 end
2957 2962
2958 2963 def test_bulk_copy_should_allow_changing_the_issue_attributes
2959 2964 # Fixes random test failure with Mysql
2960 2965 # where Issue.all(:limit => 2, :order => 'id desc', :conditions => {:project_id => 2})
2961 2966 # doesn't return the expected results
2962 2967 Issue.delete_all("project_id=2")
2963 2968
2964 2969 @request.session[:user_id] = 2
2965 2970 assert_difference 'Issue.count', 2 do
2966 2971 assert_no_difference 'Project.find(1).issues.count' do
2967 2972 post :bulk_update, :ids => [1, 2], :copy => '1',
2968 2973 :issue => {
2969 2974 :project_id => '2', :tracker_id => '', :assigned_to_id => '4',
2970 2975 :status_id => '3', :start_date => '2009-12-01', :due_date => '2009-12-31'
2971 2976 }
2972 2977 end
2973 2978 end
2974 2979
2975 2980 copied_issues = Issue.all(:limit => 2, :order => 'id desc', :conditions => {:project_id => 2})
2976 2981 assert_equal 2, copied_issues.size
2977 2982 copied_issues.each do |issue|
2978 2983 assert_equal 2, issue.project_id, "Project is incorrect"
2979 2984 assert_equal 4, issue.assigned_to_id, "Assigned to is incorrect"
2980 2985 assert_equal 3, issue.status_id, "Status is incorrect"
2981 2986 assert_equal '2009-12-01', issue.start_date.to_s, "Start date is incorrect"
2982 2987 assert_equal '2009-12-31', issue.due_date.to_s, "Due date is incorrect"
2983 2988 end
2984 2989 end
2985 2990
2986 2991 def test_bulk_copy_should_allow_adding_a_note
2987 2992 @request.session[:user_id] = 2
2988 2993 assert_difference 'Issue.count', 1 do
2989 2994 post :bulk_update, :ids => [1], :copy => '1',
2990 2995 :notes => 'Copying one issue',
2991 2996 :issue => {
2992 2997 :project_id => '', :tracker_id => '', :assigned_to_id => '4',
2993 2998 :status_id => '3', :start_date => '2009-12-01', :due_date => '2009-12-31'
2994 2999 }
2995 3000 end
2996 3001
2997 3002 issue = Issue.first(:order => 'id DESC')
2998 3003 assert_equal 1, issue.journals.size
2999 3004 journal = issue.journals.first
3000 3005 assert_equal 0, journal.details.size
3001 3006 assert_equal 'Copying one issue', journal.notes
3002 3007 end
3003 3008
3004 3009 def test_bulk_copy_to_another_project_should_follow_when_needed
3005 3010 @request.session[:user_id] = 2
3006 3011 post :bulk_update, :ids => [1], :copy => '1', :issue => {:project_id => 2}, :follow => '1'
3007 3012 issue = Issue.first(:order => 'id DESC')
3008 3013 assert_redirected_to :controller => 'issues', :action => 'show', :id => issue
3009 3014 end
3010 3015
3011 3016 def test_destroy_issue_with_no_time_entries
3012 3017 assert_nil TimeEntry.find_by_issue_id(2)
3013 3018 @request.session[:user_id] = 2
3014 3019
3015 3020 assert_difference 'Issue.count', -1 do
3016 3021 delete :destroy, :id => 2
3017 3022 end
3018 3023 assert_redirected_to :action => 'index', :project_id => 'ecookbook'
3019 3024 assert_nil Issue.find_by_id(2)
3020 3025 end
3021 3026
3022 3027 def test_destroy_issues_with_time_entries
3023 3028 @request.session[:user_id] = 2
3024 3029
3025 3030 assert_no_difference 'Issue.count' do
3026 3031 delete :destroy, :ids => [1, 3]
3027 3032 end
3028 3033 assert_response :success
3029 3034 assert_template 'destroy'
3030 3035 assert_not_nil assigns(:hours)
3031 3036 assert Issue.find_by_id(1) && Issue.find_by_id(3)
3032 3037 assert_tag 'form',
3033 3038 :descendant => {:tag => 'input', :attributes => {:name => '_method', :value => 'delete'}}
3034 3039 end
3035 3040
3036 3041 def test_destroy_issues_and_destroy_time_entries
3037 3042 @request.session[:user_id] = 2
3038 3043
3039 3044 assert_difference 'Issue.count', -2 do
3040 3045 assert_difference 'TimeEntry.count', -3 do
3041 3046 delete :destroy, :ids => [1, 3], :todo => 'destroy'
3042 3047 end
3043 3048 end
3044 3049 assert_redirected_to :action => 'index', :project_id => 'ecookbook'
3045 3050 assert !(Issue.find_by_id(1) || Issue.find_by_id(3))
3046 3051 assert_nil TimeEntry.find_by_id([1, 2])
3047 3052 end
3048 3053
3049 3054 def test_destroy_issues_and_assign_time_entries_to_project
3050 3055 @request.session[:user_id] = 2
3051 3056
3052 3057 assert_difference 'Issue.count', -2 do
3053 3058 assert_no_difference 'TimeEntry.count' do
3054 3059 delete :destroy, :ids => [1, 3], :todo => 'nullify'
3055 3060 end
3056 3061 end
3057 3062 assert_redirected_to :action => 'index', :project_id => 'ecookbook'
3058 3063 assert !(Issue.find_by_id(1) || Issue.find_by_id(3))
3059 3064 assert_nil TimeEntry.find(1).issue_id
3060 3065 assert_nil TimeEntry.find(2).issue_id
3061 3066 end
3062 3067
3063 3068 def test_destroy_issues_and_reassign_time_entries_to_another_issue
3064 3069 @request.session[:user_id] = 2
3065 3070
3066 3071 assert_difference 'Issue.count', -2 do
3067 3072 assert_no_difference 'TimeEntry.count' do
3068 3073 delete :destroy, :ids => [1, 3], :todo => 'reassign', :reassign_to_id => 2
3069 3074 end
3070 3075 end
3071 3076 assert_redirected_to :action => 'index', :project_id => 'ecookbook'
3072 3077 assert !(Issue.find_by_id(1) || Issue.find_by_id(3))
3073 3078 assert_equal 2, TimeEntry.find(1).issue_id
3074 3079 assert_equal 2, TimeEntry.find(2).issue_id
3075 3080 end
3076 3081
3077 3082 def test_destroy_issues_from_different_projects
3078 3083 @request.session[:user_id] = 2
3079 3084
3080 3085 assert_difference 'Issue.count', -3 do
3081 3086 delete :destroy, :ids => [1, 2, 6], :todo => 'destroy'
3082 3087 end
3083 3088 assert_redirected_to :controller => 'issues', :action => 'index'
3084 3089 assert !(Issue.find_by_id(1) || Issue.find_by_id(2) || Issue.find_by_id(6))
3085 3090 end
3086 3091
3087 3092 def test_destroy_parent_and_child_issues
3088 3093 parent = Issue.create!(:project_id => 1, :author_id => 1, :tracker_id => 1, :subject => 'Parent Issue')
3089 3094 child = Issue.create!(:project_id => 1, :author_id => 1, :tracker_id => 1, :subject => 'Child Issue', :parent_issue_id => parent.id)
3090 3095 assert child.is_descendant_of?(parent.reload)
3091 3096
3092 3097 @request.session[:user_id] = 2
3093 3098 assert_difference 'Issue.count', -2 do
3094 3099 delete :destroy, :ids => [parent.id, child.id], :todo => 'destroy'
3095 3100 end
3096 3101 assert_response 302
3097 3102 end
3098 3103
3099 3104 def test_default_search_scope
3100 3105 get :index
3101 3106 assert_tag :div, :attributes => {:id => 'quick-search'},
3102 3107 :child => {:tag => 'form',
3103 3108 :child => {:tag => 'input', :attributes => {:name => 'issues', :type => 'hidden', :value => '1'}}}
3104 3109 end
3105 3110 end
General Comments 0
You need to be logged in to leave comments. Login now