You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

issue_relation_test.rb 9.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266
  1. # frozen_string_literal: true
  2. # Redmine - project management software
  3. # Copyright (C) 2006- Jean-Philippe Lang
  4. #
  5. # This program is free software; you can redistribute it and/or
  6. # modify it under the terms of the GNU General Public License
  7. # as published by the Free Software Foundation; either version 2
  8. # of the License, or (at your option) any later version.
  9. #
  10. # This program is distributed in the hope that it will be useful,
  11. # but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. # GNU General Public License for more details.
  14. #
  15. # You should have received a copy of the GNU General Public License
  16. # along with this program; if not, write to the Free Software
  17. # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
  18. require_relative '../test_helper'
  19. class IssueRelationTest < ActiveSupport::TestCase
  20. fixtures :projects,
  21. :users,
  22. :roles,
  23. :members,
  24. :member_roles,
  25. :issues,
  26. :issue_statuses,
  27. :issue_relations,
  28. :enabled_modules,
  29. :enumerations,
  30. :trackers,
  31. :projects_trackers
  32. include Redmine::I18n
  33. def setup
  34. User.current = nil
  35. end
  36. def test_create
  37. from = Issue.find(1)
  38. to = Issue.find(2)
  39. relation = IssueRelation.new :issue_from => from, :issue_to => to,
  40. :relation_type => IssueRelation::TYPE_PRECEDES
  41. assert relation.save
  42. relation.reload
  43. assert_equal IssueRelation::TYPE_PRECEDES, relation.relation_type
  44. assert_equal from, relation.issue_from
  45. assert_equal to, relation.issue_to
  46. end
  47. def test_create_minimum
  48. relation = IssueRelation.new :issue_from => Issue.find(1), :issue_to => Issue.find(2)
  49. assert relation.save
  50. assert_equal IssueRelation::TYPE_RELATES, relation.relation_type
  51. end
  52. def test_follows_relation_should_be_reversed
  53. from = Issue.find(1)
  54. to = Issue.find(2)
  55. relation = IssueRelation.new :issue_from => from, :issue_to => to,
  56. :relation_type => IssueRelation::TYPE_FOLLOWS
  57. assert relation.save
  58. relation.reload
  59. assert_equal IssueRelation::TYPE_PRECEDES, relation.relation_type
  60. assert_equal to, relation.issue_from
  61. assert_equal from, relation.issue_to
  62. end
  63. def test_cannot_create_inverse_relates_relations
  64. from = Issue.find(1)
  65. to = Issue.find(2)
  66. relation1 = IssueRelation.new :issue_from => from, :issue_to => to,
  67. :relation_type => IssueRelation::TYPE_RELATES
  68. assert relation1.save
  69. relation2 = IssueRelation.new :issue_from => to, :issue_to => from,
  70. :relation_type => IssueRelation::TYPE_RELATES
  71. assert !relation2.save
  72. assert_not_equal [], relation2.errors[:base]
  73. end
  74. def test_follows_relation_should_not_be_reversed_if_validation_fails
  75. from = Issue.find(1)
  76. to = Issue.find(2)
  77. relation = IssueRelation.new :issue_from => from, :issue_to => to,
  78. :relation_type => IssueRelation::TYPE_FOLLOWS,
  79. :delay => 'xx'
  80. assert !relation.save
  81. assert_equal IssueRelation::TYPE_FOLLOWS, relation.relation_type
  82. assert_equal from, relation.issue_from
  83. assert_equal to, relation.issue_to
  84. end
  85. def test_relation_type_for
  86. from = Issue.find(1)
  87. to = Issue.find(2)
  88. relation = IssueRelation.new :issue_from => from, :issue_to => to,
  89. :relation_type => IssueRelation::TYPE_PRECEDES
  90. assert_equal IssueRelation::TYPE_PRECEDES, relation.relation_type_for(from)
  91. assert_equal IssueRelation::TYPE_FOLLOWS, relation.relation_type_for(to)
  92. end
  93. def test_set_issue_to_dates_without_issue_to
  94. r = IssueRelation.new(:issue_from => Issue.new(:start_date => Date.today),
  95. :relation_type => IssueRelation::TYPE_PRECEDES,
  96. :delay => 1)
  97. assert_nil r.set_issue_to_dates
  98. end
  99. def test_set_issue_to_dates_without_issues
  100. r = IssueRelation.new(:relation_type => IssueRelation::TYPE_PRECEDES, :delay => 1)
  101. assert_nil r.set_issue_to_dates
  102. end
  103. def test_validates_circular_dependency
  104. IssueRelation.delete_all
  105. assert(
  106. IssueRelation.create!(
  107. :issue_from => Issue.find(1), :issue_to => Issue.find(2),
  108. :relation_type => IssueRelation::TYPE_PRECEDES
  109. )
  110. )
  111. assert(
  112. IssueRelation.create!(
  113. :issue_from => Issue.find(2), :issue_to => Issue.find(3),
  114. :relation_type => IssueRelation::TYPE_PRECEDES
  115. )
  116. )
  117. r =
  118. IssueRelation.new(
  119. :issue_from => Issue.find(3), :issue_to => Issue.find(1),
  120. :relation_type => IssueRelation::TYPE_PRECEDES
  121. )
  122. assert !r.save
  123. assert_not_equal [], r.errors[:base]
  124. end
  125. def test_validates_circular_dependency_of_subtask
  126. set_language_if_valid 'en'
  127. issue1 = Issue.generate!
  128. issue2 = Issue.generate!
  129. IssueRelation.create!(
  130. :issue_from => issue1, :issue_to => issue2,
  131. :relation_type => IssueRelation::TYPE_PRECEDES
  132. )
  133. child = Issue.generate!(:parent_issue_id => issue2.id)
  134. issue1.reload
  135. child.reload
  136. r =
  137. IssueRelation.new(
  138. :issue_from => child, :issue_to => issue1,
  139. :relation_type => IssueRelation::TYPE_PRECEDES
  140. )
  141. assert !r.save
  142. assert_include 'This relation would create a circular dependency', r.errors.full_messages
  143. end
  144. def test_subtasks_should_allow_precedes_relation
  145. parent = Issue.generate!
  146. child1 = Issue.generate!(:parent_issue_id => parent.id)
  147. child2 = Issue.generate!(:parent_issue_id => parent.id)
  148. r =
  149. IssueRelation.new(
  150. :issue_from => child1, :issue_to => child2,
  151. :relation_type => IssueRelation::TYPE_PRECEDES
  152. )
  153. assert r.valid?
  154. assert r.save
  155. end
  156. def test_validates_circular_dependency_on_reverse_relations
  157. IssueRelation.delete_all
  158. assert(
  159. IssueRelation.create!(
  160. :issue_from => Issue.find(1), :issue_to => Issue.find(3),
  161. :relation_type => IssueRelation::TYPE_BLOCKS
  162. )
  163. )
  164. assert(
  165. IssueRelation.create!(
  166. :issue_from => Issue.find(1), :issue_to => Issue.find(2),
  167. :relation_type => IssueRelation::TYPE_BLOCKED
  168. )
  169. )
  170. r =
  171. IssueRelation.new(
  172. :issue_from => Issue.find(2), :issue_to => Issue.find(1),
  173. :relation_type => IssueRelation::TYPE_BLOCKED
  174. )
  175. assert !r.save
  176. assert_not_equal [], r.errors[:base]
  177. end
  178. def test_create_with_initialized_journals_should_create_journals
  179. from = Issue.find(1)
  180. to = Issue.find(2)
  181. from_journals = from.journals.size
  182. to_journals = to.journals.size
  183. relation = IssueRelation.new(:issue_from => from, :issue_to => to,
  184. :relation_type => IssueRelation::TYPE_PRECEDES)
  185. relation.init_journals User.find(1)
  186. assert relation.save
  187. from.reload
  188. to.reload
  189. relation.reload
  190. assert_equal from.journals.size, (from_journals + 1)
  191. assert_equal to.journals.size, (to_journals + 1)
  192. assert_equal 'relation', from.journals.last.details.last.property
  193. assert_equal 'precedes', from.journals.last.details.last.prop_key
  194. assert_equal '2', from.journals.last.details.last.value
  195. assert_nil from.journals.last.details.last.old_value
  196. assert_equal 'relation', to.journals.last.details.last.property
  197. assert_equal 'follows', to.journals.last.details.last.prop_key
  198. assert_equal '1', to.journals.last.details.last.value
  199. assert_nil to.journals.last.details.last.old_value
  200. end
  201. def test_destroy_with_initialized_journals_should_create_journals
  202. relation = IssueRelation.find(1)
  203. from = relation.issue_from
  204. to = relation.issue_to
  205. from_journals = from.journals.size
  206. to_journals = to.journals.size
  207. relation.init_journals User.find(1)
  208. assert relation.destroy
  209. from.reload
  210. to.reload
  211. assert_equal from.journals.size, (from_journals + 1)
  212. assert_equal to.journals.size, (to_journals + 1)
  213. assert_equal 'relation', from.journals.last.details.last.property
  214. assert_equal 'blocks', from.journals.last.details.last.prop_key
  215. assert_equal '9', from.journals.last.details.last.old_value
  216. assert_nil from.journals.last.details.last.value
  217. assert_equal 'relation', to.journals.last.details.last.property
  218. assert_equal 'blocked', to.journals.last.details.last.prop_key
  219. assert_equal '10', to.journals.last.details.last.old_value
  220. assert_nil to.journals.last.details.last.value
  221. end
  222. def test_to_s_should_return_the_relation_string
  223. set_language_if_valid 'en'
  224. relation = IssueRelation.find(1)
  225. assert_equal "Blocks #9", relation.to_s(relation.issue_from)
  226. assert_equal "Blocked by #10", relation.to_s(relation.issue_to)
  227. end
  228. def test_to_s_without_argument_should_return_the_relation_string_for_issue_from
  229. set_language_if_valid 'en'
  230. relation = IssueRelation.find(1)
  231. assert_equal "Blocks #9", relation.to_s
  232. end
  233. def test_to_s_should_accept_a_block_as_custom_issue_formatting
  234. set_language_if_valid 'en'
  235. relation = IssueRelation.find(1)
  236. assert_equal "Blocks Bug #9", relation.to_s {|issue| "#{issue.tracker} ##{issue.id}"}
  237. end
  238. end