Mercurial > hg > soundsoftware-site
comparison .svn/pristine/5d/5d77150ffce84de102397cf62ea517a3fc5da2e0.svn-base @ 1494:e248c7af89ec redmine-2.4
Update to Redmine SVN revision 12979 on 2.4-stable branch
author | Chris Cannam |
---|---|
date | Mon, 17 Mar 2014 08:54:02 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
1464:261b3d9a4903 | 1494:e248c7af89ec |
---|---|
1 # encoding: utf-8 | |
2 # | |
3 # Redmine - project management software | |
4 # Copyright (C) 2006-2014 Jean-Philippe Lang | |
5 # | |
6 # This program is free software; you can redistribute it and/or | |
7 # modify it under the terms of the GNU General Public License | |
8 # as published by the Free Software Foundation; either version 2 | |
9 # of the License, or (at your option) any later version. | |
10 # | |
11 # This program is distributed in the hope that it will be useful, | |
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
14 # GNU General Public License for more details. | |
15 # | |
16 # You should have received a copy of the GNU General Public License | |
17 # along with this program; if not, write to the Free Software | |
18 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. | |
19 | |
20 require File.expand_path('../../test_helper', __FILE__) | |
21 | |
22 class ChangesetTest < ActiveSupport::TestCase | |
23 fixtures :projects, :repositories, | |
24 :issues, :issue_statuses, :issue_categories, | |
25 :changesets, :changes, | |
26 :enumerations, | |
27 :custom_fields, :custom_values, | |
28 :users, :members, :member_roles, :trackers, | |
29 :enabled_modules, :roles | |
30 | |
31 def test_ref_keywords_any | |
32 ActionMailer::Base.deliveries.clear | |
33 Setting.commit_ref_keywords = '*' | |
34 Setting.commit_update_keywords = [{'keywords' => 'fixes , closes', 'status_id' => '5', 'done_ratio' => '90'}] | |
35 | |
36 c = Changeset.new(:repository => Project.find(1).repository, | |
37 :committed_on => Time.now, | |
38 :comments => 'New commit (#2). Fixes #1', | |
39 :revision => '12345') | |
40 assert c.save | |
41 assert_equal [1, 2], c.issue_ids.sort | |
42 fixed = Issue.find(1) | |
43 assert fixed.closed? | |
44 assert_equal 90, fixed.done_ratio | |
45 assert_equal 1, ActionMailer::Base.deliveries.size | |
46 end | |
47 | |
48 def test_ref_keywords | |
49 Setting.commit_ref_keywords = 'refs' | |
50 Setting.commit_update_keywords = '' | |
51 c = Changeset.new(:repository => Project.find(1).repository, | |
52 :committed_on => Time.now, | |
53 :comments => 'Ignores #2. Refs #1', | |
54 :revision => '12345') | |
55 assert c.save | |
56 assert_equal [1], c.issue_ids.sort | |
57 end | |
58 | |
59 def test_ref_keywords_any_only | |
60 Setting.commit_ref_keywords = '*' | |
61 Setting.commit_update_keywords = '' | |
62 c = Changeset.new(:repository => Project.find(1).repository, | |
63 :committed_on => Time.now, | |
64 :comments => 'Ignores #2. Refs #1', | |
65 :revision => '12345') | |
66 assert c.save | |
67 assert_equal [1, 2], c.issue_ids.sort | |
68 end | |
69 | |
70 def test_ref_keywords_any_with_timelog | |
71 Setting.commit_ref_keywords = '*' | |
72 Setting.commit_logtime_enabled = '1' | |
73 | |
74 { | |
75 '2' => 2.0, | |
76 '2h' => 2.0, | |
77 '2hours' => 2.0, | |
78 '15m' => 0.25, | |
79 '15min' => 0.25, | |
80 '3h15' => 3.25, | |
81 '3h15m' => 3.25, | |
82 '3h15min' => 3.25, | |
83 '3:15' => 3.25, | |
84 '3.25' => 3.25, | |
85 '3.25h' => 3.25, | |
86 '3,25' => 3.25, | |
87 '3,25h' => 3.25, | |
88 }.each do |syntax, expected_hours| | |
89 c = Changeset.new(:repository => Project.find(1).repository, | |
90 :committed_on => 24.hours.ago, | |
91 :comments => "Worked on this issue #1 @#{syntax}", | |
92 :revision => '520', | |
93 :user => User.find(2)) | |
94 assert_difference 'TimeEntry.count' do | |
95 c.scan_comment_for_issue_ids | |
96 end | |
97 assert_equal [1], c.issue_ids.sort | |
98 | |
99 time = TimeEntry.first(:order => 'id desc') | |
100 assert_equal 1, time.issue_id | |
101 assert_equal 1, time.project_id | |
102 assert_equal 2, time.user_id | |
103 assert_equal expected_hours, time.hours, | |
104 "@#{syntax} should be logged as #{expected_hours} hours but was #{time.hours}" | |
105 assert_equal Date.yesterday, time.spent_on | |
106 assert time.activity.is_default? | |
107 assert time.comments.include?('r520'), | |
108 "r520 was expected in time_entry comments: #{time.comments}" | |
109 end | |
110 end | |
111 | |
112 def test_ref_keywords_closing_with_timelog | |
113 Setting.commit_ref_keywords = '*' | |
114 Setting.commit_update_keywords = [{'keywords' => 'fixes , closes', 'status_id' => IssueStatus.where(:is_closed => true).first.id.to_s}] | |
115 Setting.commit_logtime_enabled = '1' | |
116 | |
117 c = Changeset.new(:repository => Project.find(1).repository, | |
118 :committed_on => Time.now, | |
119 :comments => 'This is a comment. Fixes #1 @4.5, #2 @1', | |
120 :user => User.find(2)) | |
121 assert_difference 'TimeEntry.count', 2 do | |
122 c.scan_comment_for_issue_ids | |
123 end | |
124 | |
125 assert_equal [1, 2], c.issue_ids.sort | |
126 assert Issue.find(1).closed? | |
127 assert Issue.find(2).closed? | |
128 | |
129 times = TimeEntry.all(:order => 'id desc', :limit => 2) | |
130 assert_equal [1, 2], times.collect(&:issue_id).sort | |
131 end | |
132 | |
133 def test_ref_keywords_any_line_start | |
134 Setting.commit_ref_keywords = '*' | |
135 c = Changeset.new(:repository => Project.find(1).repository, | |
136 :committed_on => Time.now, | |
137 :comments => '#1 is the reason of this commit', | |
138 :revision => '12345') | |
139 assert c.save | |
140 assert_equal [1], c.issue_ids.sort | |
141 end | |
142 | |
143 def test_ref_keywords_allow_brackets_around_a_issue_number | |
144 Setting.commit_ref_keywords = '*' | |
145 c = Changeset.new(:repository => Project.find(1).repository, | |
146 :committed_on => Time.now, | |
147 :comments => '[#1] Worked on this issue', | |
148 :revision => '12345') | |
149 assert c.save | |
150 assert_equal [1], c.issue_ids.sort | |
151 end | |
152 | |
153 def test_ref_keywords_allow_brackets_around_multiple_issue_numbers | |
154 Setting.commit_ref_keywords = '*' | |
155 c = Changeset.new(:repository => Project.find(1).repository, | |
156 :committed_on => Time.now, | |
157 :comments => '[#1 #2, #3] Worked on these', | |
158 :revision => '12345') | |
159 assert c.save | |
160 assert_equal [1,2,3], c.issue_ids.sort | |
161 end | |
162 | |
163 def test_update_keywords_with_multiple_rules | |
164 with_settings :commit_update_keywords => [ | |
165 {'keywords' => 'fixes, closes', 'status_id' => '5'}, | |
166 {'keywords' => 'resolves', 'status_id' => '3'} | |
167 ] do | |
168 | |
169 issue1 = Issue.generate! | |
170 issue2 = Issue.generate! | |
171 Changeset.generate!(:comments => "Closes ##{issue1.id}\nResolves ##{issue2.id}") | |
172 assert_equal 5, issue1.reload.status_id | |
173 assert_equal 3, issue2.reload.status_id | |
174 end | |
175 end | |
176 | |
177 def test_update_keywords_with_multiple_rules_should_match_tracker | |
178 with_settings :commit_update_keywords => [ | |
179 {'keywords' => 'fixes', 'status_id' => '5', 'if_tracker_id' => '2'}, | |
180 {'keywords' => 'fixes', 'status_id' => '3', 'if_tracker_id' => ''} | |
181 ] do | |
182 | |
183 issue1 = Issue.generate!(:tracker_id => 2) | |
184 issue2 = Issue.generate! | |
185 Changeset.generate!(:comments => "Fixes ##{issue1.id}, ##{issue2.id}") | |
186 assert_equal 5, issue1.reload.status_id | |
187 assert_equal 3, issue2.reload.status_id | |
188 end | |
189 end | |
190 | |
191 def test_update_keywords_with_multiple_rules_and_no_match | |
192 with_settings :commit_update_keywords => [ | |
193 {'keywords' => 'fixes', 'status_id' => '5', 'if_tracker_id' => '2'}, | |
194 {'keywords' => 'fixes', 'status_id' => '3', 'if_tracker_id' => '3'} | |
195 ] do | |
196 | |
197 issue1 = Issue.generate!(:tracker_id => 2) | |
198 issue2 = Issue.generate! | |
199 Changeset.generate!(:comments => "Fixes ##{issue1.id}, ##{issue2.id}") | |
200 assert_equal 5, issue1.reload.status_id | |
201 assert_equal 1, issue2.reload.status_id # no updates | |
202 end | |
203 end | |
204 | |
205 def test_commit_referencing_a_subproject_issue | |
206 c = Changeset.new(:repository => Project.find(1).repository, | |
207 :committed_on => Time.now, | |
208 :comments => 'refs #5, a subproject issue', | |
209 :revision => '12345') | |
210 assert c.save | |
211 assert_equal [5], c.issue_ids.sort | |
212 assert c.issues.first.project != c.project | |
213 end | |
214 | |
215 def test_commit_closing_a_subproject_issue | |
216 with_settings :commit_update_keywords => [{'keywords' => 'closes', 'status_id' => '5'}], | |
217 :default_language => 'en' do | |
218 issue = Issue.find(5) | |
219 assert !issue.closed? | |
220 assert_difference 'Journal.count' do | |
221 c = Changeset.new(:repository => Project.find(1).repository, | |
222 :committed_on => Time.now, | |
223 :comments => 'closes #5, a subproject issue', | |
224 :revision => '12345') | |
225 assert c.save | |
226 end | |
227 assert issue.reload.closed? | |
228 journal = Journal.first(:order => 'id DESC') | |
229 assert_equal issue, journal.issue | |
230 assert_include "Applied in changeset ecookbook:r12345.", journal.notes | |
231 end | |
232 end | |
233 | |
234 def test_commit_referencing_a_parent_project_issue | |
235 # repository of child project | |
236 r = Repository::Subversion.create!( | |
237 :project => Project.find(3), | |
238 :url => 'svn://localhost/test') | |
239 c = Changeset.new(:repository => r, | |
240 :committed_on => Time.now, | |
241 :comments => 'refs #2, an issue of a parent project', | |
242 :revision => '12345') | |
243 assert c.save | |
244 assert_equal [2], c.issue_ids.sort | |
245 assert c.issues.first.project != c.project | |
246 end | |
247 | |
248 def test_commit_referencing_a_project_with_commit_cross_project_ref_disabled | |
249 r = Repository::Subversion.create!( | |
250 :project => Project.find(3), | |
251 :url => 'svn://localhost/test') | |
252 | |
253 with_settings :commit_cross_project_ref => '0' do | |
254 c = Changeset.new(:repository => r, | |
255 :committed_on => Time.now, | |
256 :comments => 'refs #4, an issue of a different project', | |
257 :revision => '12345') | |
258 assert c.save | |
259 assert_equal [], c.issue_ids | |
260 end | |
261 end | |
262 | |
263 def test_commit_referencing_a_project_with_commit_cross_project_ref_enabled | |
264 r = Repository::Subversion.create!( | |
265 :project => Project.find(3), | |
266 :url => 'svn://localhost/test') | |
267 | |
268 with_settings :commit_cross_project_ref => '1' do | |
269 c = Changeset.new(:repository => r, | |
270 :committed_on => Time.now, | |
271 :comments => 'refs #4, an issue of a different project', | |
272 :revision => '12345') | |
273 assert c.save | |
274 assert_equal [4], c.issue_ids | |
275 end | |
276 end | |
277 | |
278 def test_old_commits_should_not_update_issues_nor_log_time | |
279 Setting.commit_ref_keywords = '*' | |
280 Setting.commit_update_keywords = {'fixes , closes' => {'status_id' => '5', 'done_ratio' => '90'}} | |
281 Setting.commit_logtime_enabled = '1' | |
282 | |
283 repository = Project.find(1).repository | |
284 repository.created_on = Time.now | |
285 repository.save! | |
286 | |
287 c = Changeset.new(:repository => repository, | |
288 :committed_on => 1.month.ago, | |
289 :comments => 'New commit (#2). Fixes #1 @1h', | |
290 :revision => '12345') | |
291 assert_no_difference 'TimeEntry.count' do | |
292 assert c.save | |
293 end | |
294 assert_equal [1, 2], c.issue_ids.sort | |
295 issue = Issue.find(1) | |
296 assert_equal 1, issue.status_id | |
297 assert_equal 0, issue.done_ratio | |
298 end | |
299 | |
300 def test_text_tag_revision | |
301 c = Changeset.new(:revision => '520') | |
302 assert_equal 'r520', c.text_tag | |
303 end | |
304 | |
305 def test_text_tag_revision_with_same_project | |
306 c = Changeset.new(:revision => '520', :repository => Project.find(1).repository) | |
307 assert_equal 'r520', c.text_tag(Project.find(1)) | |
308 end | |
309 | |
310 def test_text_tag_revision_with_different_project | |
311 c = Changeset.new(:revision => '520', :repository => Project.find(1).repository) | |
312 assert_equal 'ecookbook:r520', c.text_tag(Project.find(2)) | |
313 end | |
314 | |
315 def test_text_tag_revision_with_repository_identifier | |
316 r = Repository::Subversion.create!( | |
317 :project_id => 1, | |
318 :url => 'svn://localhost/test', | |
319 :identifier => 'documents') | |
320 | |
321 c = Changeset.new(:revision => '520', :repository => r) | |
322 assert_equal 'documents|r520', c.text_tag | |
323 assert_equal 'ecookbook:documents|r520', c.text_tag(Project.find(2)) | |
324 end | |
325 | |
326 def test_text_tag_hash | |
327 c = Changeset.new( | |
328 :scmid => '7234cb2750b63f47bff735edc50a1c0a433c2518', | |
329 :revision => '7234cb2750b63f47bff735edc50a1c0a433c2518') | |
330 assert_equal 'commit:7234cb2750b63f47bff735edc50a1c0a433c2518', c.text_tag | |
331 end | |
332 | |
333 def test_text_tag_hash_with_same_project | |
334 c = Changeset.new(:revision => '7234cb27', :scmid => '7234cb27', :repository => Project.find(1).repository) | |
335 assert_equal 'commit:7234cb27', c.text_tag(Project.find(1)) | |
336 end | |
337 | |
338 def test_text_tag_hash_with_different_project | |
339 c = Changeset.new(:revision => '7234cb27', :scmid => '7234cb27', :repository => Project.find(1).repository) | |
340 assert_equal 'ecookbook:commit:7234cb27', c.text_tag(Project.find(2)) | |
341 end | |
342 | |
343 def test_text_tag_hash_all_number | |
344 c = Changeset.new(:scmid => '0123456789', :revision => '0123456789') | |
345 assert_equal 'commit:0123456789', c.text_tag | |
346 end | |
347 | |
348 def test_text_tag_hash_with_repository_identifier | |
349 r = Repository::Subversion.new( | |
350 :project_id => 1, | |
351 :url => 'svn://localhost/test', | |
352 :identifier => 'documents') | |
353 c = Changeset.new(:revision => '7234cb27', :scmid => '7234cb27', :repository => r) | |
354 assert_equal 'commit:documents|7234cb27', c.text_tag | |
355 assert_equal 'ecookbook:commit:documents|7234cb27', c.text_tag(Project.find(2)) | |
356 end | |
357 | |
358 def test_previous | |
359 changeset = Changeset.find_by_revision('3') | |
360 assert_equal Changeset.find_by_revision('2'), changeset.previous | |
361 end | |
362 | |
363 def test_previous_nil | |
364 changeset = Changeset.find_by_revision('1') | |
365 assert_nil changeset.previous | |
366 end | |
367 | |
368 def test_next | |
369 changeset = Changeset.find_by_revision('2') | |
370 assert_equal Changeset.find_by_revision('3'), changeset.next | |
371 end | |
372 | |
373 def test_next_nil | |
374 changeset = Changeset.find_by_revision('10') | |
375 assert_nil changeset.next | |
376 end | |
377 | |
378 def test_comments_should_be_converted_to_utf8 | |
379 proj = Project.find(3) | |
380 # str = File.read("#{RAILS_ROOT}/test/fixtures/encoding/iso-8859-1.txt") | |
381 str = "Texte encod\xe9 en ISO-8859-1." | |
382 str.force_encoding("ASCII-8BIT") if str.respond_to?(:force_encoding) | |
383 r = Repository::Bazaar.create!( | |
384 :project => proj, | |
385 :url => '/tmp/test/bazaar', | |
386 :log_encoding => 'ISO-8859-1' ) | |
387 assert r | |
388 c = Changeset.new(:repository => r, | |
389 :committed_on => Time.now, | |
390 :revision => '123', | |
391 :scmid => '12345', | |
392 :comments => str) | |
393 assert( c.save ) | |
394 str_utf8 = "Texte encod\xc3\xa9 en ISO-8859-1." | |
395 str_utf8.force_encoding("UTF-8") if str_utf8.respond_to?(:force_encoding) | |
396 assert_equal str_utf8, c.comments | |
397 end | |
398 | |
399 def test_invalid_utf8_sequences_in_comments_should_be_replaced_latin1 | |
400 proj = Project.find(3) | |
401 # str = File.read("#{RAILS_ROOT}/test/fixtures/encoding/iso-8859-1.txt") | |
402 str1 = "Texte encod\xe9 en ISO-8859-1." | |
403 str2 = "\xe9a\xe9b\xe9c\xe9d\xe9e test" | |
404 str1.force_encoding("UTF-8") if str1.respond_to?(:force_encoding) | |
405 str2.force_encoding("ASCII-8BIT") if str2.respond_to?(:force_encoding) | |
406 r = Repository::Bazaar.create!( | |
407 :project => proj, | |
408 :url => '/tmp/test/bazaar', | |
409 :log_encoding => 'UTF-8' ) | |
410 assert r | |
411 c = Changeset.new(:repository => r, | |
412 :committed_on => Time.now, | |
413 :revision => '123', | |
414 :scmid => '12345', | |
415 :comments => str1, | |
416 :committer => str2) | |
417 assert( c.save ) | |
418 assert_equal "Texte encod? en ISO-8859-1.", c.comments | |
419 assert_equal "?a?b?c?d?e test", c.committer | |
420 end | |
421 | |
422 def test_invalid_utf8_sequences_in_comments_should_be_replaced_ja_jis | |
423 proj = Project.find(3) | |
424 str = "test\xb5\xfetest\xb5\xfe" | |
425 if str.respond_to?(:force_encoding) | |
426 str.force_encoding('ASCII-8BIT') | |
427 end | |
428 r = Repository::Bazaar.create!( | |
429 :project => proj, | |
430 :url => '/tmp/test/bazaar', | |
431 :log_encoding => 'ISO-2022-JP' ) | |
432 assert r | |
433 c = Changeset.new(:repository => r, | |
434 :committed_on => Time.now, | |
435 :revision => '123', | |
436 :scmid => '12345', | |
437 :comments => str) | |
438 assert( c.save ) | |
439 assert_equal "test??test??", c.comments | |
440 end | |
441 | |
442 def test_comments_should_be_converted_all_latin1_to_utf8 | |
443 s1 = "\xC2\x80" | |
444 s2 = "\xc3\x82\xc2\x80" | |
445 s4 = s2.dup | |
446 if s1.respond_to?(:force_encoding) | |
447 s3 = s1.dup | |
448 s1.force_encoding('ASCII-8BIT') | |
449 s2.force_encoding('ASCII-8BIT') | |
450 s3.force_encoding('ISO-8859-1') | |
451 s4.force_encoding('UTF-8') | |
452 assert_equal s3.encode('UTF-8'), s4 | |
453 end | |
454 proj = Project.find(3) | |
455 r = Repository::Bazaar.create!( | |
456 :project => proj, | |
457 :url => '/tmp/test/bazaar', | |
458 :log_encoding => 'ISO-8859-1' ) | |
459 assert r | |
460 c = Changeset.new(:repository => r, | |
461 :committed_on => Time.now, | |
462 :revision => '123', | |
463 :scmid => '12345', | |
464 :comments => s1) | |
465 assert( c.save ) | |
466 assert_equal s4, c.comments | |
467 end | |
468 | |
469 def test_invalid_utf8_sequences_in_paths_should_be_replaced | |
470 proj = Project.find(3) | |
471 str1 = "Texte encod\xe9 en ISO-8859-1" | |
472 str2 = "\xe9a\xe9b\xe9c\xe9d\xe9e test" | |
473 str1.force_encoding("UTF-8") if str1.respond_to?(:force_encoding) | |
474 str2.force_encoding("ASCII-8BIT") if str2.respond_to?(:force_encoding) | |
475 r = Repository::Bazaar.create!( | |
476 :project => proj, | |
477 :url => '/tmp/test/bazaar', | |
478 :log_encoding => 'UTF-8' ) | |
479 assert r | |
480 cs = Changeset.new( | |
481 :repository => r, | |
482 :committed_on => Time.now, | |
483 :revision => '123', | |
484 :scmid => '12345', | |
485 :comments => "test") | |
486 assert(cs.save) | |
487 ch = Change.new( | |
488 :changeset => cs, | |
489 :action => "A", | |
490 :path => str1, | |
491 :from_path => str2, | |
492 :from_revision => "345") | |
493 assert(ch.save) | |
494 assert_equal "Texte encod? en ISO-8859-1", ch.path | |
495 assert_equal "?a?b?c?d?e test", ch.from_path | |
496 end | |
497 | |
498 def test_comments_nil | |
499 proj = Project.find(3) | |
500 r = Repository::Bazaar.create!( | |
501 :project => proj, | |
502 :url => '/tmp/test/bazaar', | |
503 :log_encoding => 'ISO-8859-1' ) | |
504 assert r | |
505 c = Changeset.new(:repository => r, | |
506 :committed_on => Time.now, | |
507 :revision => '123', | |
508 :scmid => '12345', | |
509 :comments => nil, | |
510 :committer => nil) | |
511 assert( c.save ) | |
512 assert_equal "", c.comments | |
513 assert_equal nil, c.committer | |
514 if c.comments.respond_to?(:force_encoding) | |
515 assert_equal "UTF-8", c.comments.encoding.to_s | |
516 end | |
517 end | |
518 | |
519 def test_comments_empty | |
520 proj = Project.find(3) | |
521 r = Repository::Bazaar.create!( | |
522 :project => proj, | |
523 :url => '/tmp/test/bazaar', | |
524 :log_encoding => 'ISO-8859-1' ) | |
525 assert r | |
526 c = Changeset.new(:repository => r, | |
527 :committed_on => Time.now, | |
528 :revision => '123', | |
529 :scmid => '12345', | |
530 :comments => "", | |
531 :committer => "") | |
532 assert( c.save ) | |
533 assert_equal "", c.comments | |
534 assert_equal "", c.committer | |
535 if c.comments.respond_to?(:force_encoding) | |
536 assert_equal "UTF-8", c.comments.encoding.to_s | |
537 assert_equal "UTF-8", c.committer.encoding.to_s | |
538 end | |
539 end | |
540 | |
541 def test_identifier | |
542 c = Changeset.find_by_revision('1') | |
543 assert_equal c.revision, c.identifier | |
544 end | |
545 end |