redmineup 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (118) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +21 -0
  3. data/Gemfile +4 -0
  4. data/README.md +204 -0
  5. data/Rakefile +11 -0
  6. data/app/controllers/redmineup_controller.rb +26 -0
  7. data/app/views/redmine_crm/redmineup_calendar/_calendar.html.erb +34 -0
  8. data/app/views/redmineup/_money.html.erb +44 -0
  9. data/app/views/redmineup/settings.html.erb +10 -0
  10. data/bitbucket-pipelines.yml +50 -0
  11. data/config/currency_iso.json +2544 -0
  12. data/config/locales/cs.yml +13 -0
  13. data/config/locales/de.yml +13 -0
  14. data/config/locales/en.yml +13 -0
  15. data/config/locales/es.yml +13 -0
  16. data/config/locales/ru.yml +13 -0
  17. data/config/routes.rb +5 -0
  18. data/doc/CHANGELOG +14 -0
  19. data/doc/LICENSE.txt +339 -0
  20. data/lib/redmineup/acts_as_draftable/draft.rb +40 -0
  21. data/lib/redmineup/acts_as_draftable/up_acts_as_draftable.rb +172 -0
  22. data/lib/redmineup/acts_as_list/list.rb +282 -0
  23. data/lib/redmineup/acts_as_priceable/up_acts_as_priceable.rb +33 -0
  24. data/lib/redmineup/acts_as_taggable/tag.rb +81 -0
  25. data/lib/redmineup/acts_as_taggable/tag_list.rb +111 -0
  26. data/lib/redmineup/acts_as_taggable/tagging.rb +16 -0
  27. data/lib/redmineup/acts_as_taggable/up_acts_as_taggable.rb +357 -0
  28. data/lib/redmineup/acts_as_viewed/up_acts_as_viewed.rb +274 -0
  29. data/lib/redmineup/acts_as_votable/up_acts_as_votable.rb +80 -0
  30. data/lib/redmineup/acts_as_votable/up_acts_as_voter.rb +20 -0
  31. data/lib/redmineup/acts_as_votable/votable.rb +323 -0
  32. data/lib/redmineup/acts_as_votable/vote.rb +28 -0
  33. data/lib/redmineup/acts_as_votable/voter.rb +131 -0
  34. data/lib/redmineup/assets_manager.rb +43 -0
  35. data/lib/redmineup/colors_helper.rb +192 -0
  36. data/lib/redmineup/compatibility/application_controller_patch.rb +33 -0
  37. data/lib/redmineup/compatibility/routing_mapper_patch.rb +25 -0
  38. data/lib/redmineup/currency/formatting.rb +224 -0
  39. data/lib/redmineup/currency/heuristics.rb +151 -0
  40. data/lib/redmineup/currency/loader.rb +23 -0
  41. data/lib/redmineup/currency.rb +450 -0
  42. data/lib/redmineup/engine.rb +4 -0
  43. data/lib/redmineup/helpers/external_assets_helper.rb +20 -0
  44. data/lib/redmineup/helpers/form_tag_helper.rb +88 -0
  45. data/lib/redmineup/helpers/rup_calendar_helper.rb +146 -0
  46. data/lib/redmineup/helpers/tags_helper.rb +13 -0
  47. data/lib/redmineup/helpers/vote_helper.rb +35 -0
  48. data/lib/redmineup/hooks/views_layouts_hook.rb +11 -0
  49. data/lib/redmineup/liquid/drops/attachment_drop.rb +47 -0
  50. data/lib/redmineup/liquid/drops/issue_relations_drop.rb +41 -0
  51. data/lib/redmineup/liquid/drops/issues_drop.rb +217 -0
  52. data/lib/redmineup/liquid/drops/news_drop.rb +54 -0
  53. data/lib/redmineup/liquid/drops/projects_drop.rb +86 -0
  54. data/lib/redmineup/liquid/drops/time_entries_drop.rb +65 -0
  55. data/lib/redmineup/liquid/drops/users_drop.rb +68 -0
  56. data/lib/redmineup/liquid/filters/arrays.rb +254 -0
  57. data/lib/redmineup/liquid/filters/base.rb +249 -0
  58. data/lib/redmineup/liquid/filters/colors.rb +31 -0
  59. data/lib/redmineup/money_helper.rb +66 -0
  60. data/lib/redmineup/patches/liquid_patch.rb +33 -0
  61. data/lib/redmineup/settings/money.rb +46 -0
  62. data/lib/redmineup/settings.rb +53 -0
  63. data/lib/redmineup/version.rb +3 -0
  64. data/lib/redmineup.rb +108 -0
  65. data/redmineup.gemspec +29 -0
  66. data/test/acts_as_draftable/draft_test.rb +29 -0
  67. data/test/acts_as_draftable/rup_acts_as_draftable_test.rb +178 -0
  68. data/test/acts_as_taggable/rup_acts_as_taggable_test.rb +350 -0
  69. data/test/acts_as_taggable/tag_list_test.rb +34 -0
  70. data/test/acts_as_taggable/tag_test.rb +72 -0
  71. data/test/acts_as_taggable/tagging_test.rb +15 -0
  72. data/test/acts_as_viewed/rup_acts_as_viewed_test.rb +47 -0
  73. data/test/acts_as_votable/rup_acts_as_votable_test.rb +19 -0
  74. data/test/acts_as_votable/rup_acts_as_voter_test.rb +14 -0
  75. data/test/acts_as_votable/votable_test.rb +507 -0
  76. data/test/acts_as_votable/voter_test.rb +296 -0
  77. data/test/currency_test.rb +292 -0
  78. data/test/database.yml +17 -0
  79. data/test/fixtures/attachments.yml +14 -0
  80. data/test/fixtures/issues.yml +24 -0
  81. data/test/fixtures/news.yml +8 -0
  82. data/test/fixtures/projects.yml +10 -0
  83. data/test/fixtures/taggings.yml +32 -0
  84. data/test/fixtures/tags.yml +11 -0
  85. data/test/fixtures/users.yml +9 -0
  86. data/test/fixtures/votable_caches.yml +2 -0
  87. data/test/fixtures/votables.yml +4 -0
  88. data/test/fixtures/voters.yml +6 -0
  89. data/test/liquid/drops/attachment_drop_test.rb +15 -0
  90. data/test/liquid/drops/issue_relations_drop_test.rb +24 -0
  91. data/test/liquid/drops/issues_drop_test.rb +38 -0
  92. data/test/liquid/drops/news_drop_test.rb +38 -0
  93. data/test/liquid/drops/projects_drop_test.rb +44 -0
  94. data/test/liquid/drops/uses_drop_test.rb +36 -0
  95. data/test/liquid/filters/arrays_filter_test.rb +31 -0
  96. data/test/liquid/filters/base_filter_test.rb +67 -0
  97. data/test/liquid/filters/colors_filter_test.rb +33 -0
  98. data/test/liquid/liquid_helper.rb +34 -0
  99. data/test/models/attachment.rb +3 -0
  100. data/test/models/issue.rb +21 -0
  101. data/test/models/issue_relation.rb +10 -0
  102. data/test/models/news.rb +3 -0
  103. data/test/models/project.rb +8 -0
  104. data/test/models/user.rb +11 -0
  105. data/test/models/vote_classes.rb +33 -0
  106. data/test/money_helper_test.rb +12 -0
  107. data/test/schema.rb +144 -0
  108. data/test/tags_helper_test.rb +29 -0
  109. data/test/test_helper.rb +66 -0
  110. data/test/vote_helper_test.rb +28 -0
  111. data/vendor/assets/images/money.png +0 -0
  112. data/vendor/assets/images/vcard.png +0 -0
  113. data/vendor/assets/javascripts/Chart.bundle.min.js +16 -0
  114. data/vendor/assets/javascripts/select2.js +2 -0
  115. data/vendor/assets/javascripts/select2_helpers.js +192 -0
  116. data/vendor/assets/stylesheets/money.css +96 -0
  117. data/vendor/assets/stylesheets/select2.css +424 -0
  118. metadata +295 -0
@@ -0,0 +1,11 @@
1
+ error:
2
+ name: error
3
+
4
+ feature:
5
+ name: New feature
6
+
7
+ bug:
8
+ name: bug
9
+
10
+ question:
11
+ name: question
@@ -0,0 +1,9 @@
1
+ jonathan:
2
+ name: Jonathan
3
+ language: 'EN'
4
+ sam:
5
+ name: Sam
6
+ language: 'RU'
7
+ homer:
8
+ name: Homer
9
+ language: 'CH'
@@ -0,0 +1,2 @@
1
+ votable_cache:
2
+ name: 'votiong model with cache'
@@ -0,0 +1,4 @@
1
+ votable:
2
+ name: 'a voting model'
3
+ votable2:
4
+ name: 'another voting things'
@@ -0,0 +1,6 @@
1
+ voter:
2
+ name: 'i can vote!'
3
+ voter2:
4
+ name: 'a new person'
5
+ voter3:
6
+ name: 'another person'
@@ -0,0 +1,15 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+
3
+ module Redmineup
4
+ class AttachmentDropTest < ActiveSupport::TestCase
5
+ def setup
6
+ @attachment = attachments(:attachment_001)
7
+ @user = @attachment.author
8
+ @liquid_render = LiquidRender.new('attachment' => Liquid::AttachmentDrop.new(@attachment))
9
+ end
10
+
11
+ def test_author
12
+ assert_equal @user.name, @liquid_render.render('{{ attachment.author.name }}')
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,24 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class IssueRelationsDropTest < ActiveSupport::TestCase
6
+ def setup
7
+ @issue_from = Issue.find_by(subject: 'Issue 3 subject')
8
+ @issue_to = Issue.find_by(subject: 'Issue 4 subject')
9
+ @relation = IssueRelation.create!(issue_from: @issue_from, issue_to: @issue_to, relation_type: 'precedes', delay: 1)
10
+ @liquid_render = LiquidRender.new(
11
+ 'issue' => Liquid::IssueDrop.new(@issue_from)
12
+ )
13
+ end
14
+
15
+ def test_relation_from_render
16
+ issues_text = @liquid_render.render('{% for relation in issue.relations_from %} {{relation.issue_from.id}}|{{relation.issue_to.id}}|{{relation.relation_type}}|{{relation.delay}} {% endfor %}')
17
+ assert_match "#{@issue_from.id}|#{@issue_to.id}|precedes|#{@relation.delay}", issues_text
18
+ end
19
+
20
+ def test_relation_size
21
+ assert_equal '1', @liquid_render.render('{{ issue.relations_from.size }}')
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,38 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class IssuesDropTest < ActiveSupport::TestCase
6
+ def setup
7
+ @issue = Issue.first
8
+ @user = User.first
9
+ @liquid_render = LiquidRender.new('user' => Liquid::UserDrop.new(@user),
10
+ 'issue' => Liquid::IssueDrop.new(@issue),
11
+ 'issues' => Liquid::IssuesDrop.new(Issue.all))
12
+ end
13
+
14
+ def test_issues_all
15
+ issues_text = @liquid_render.render('{% for issue in issues.all %} {{issue.subject }} {% endfor %}')
16
+ Issue.all.map(&:subject).each do |subject|
17
+ assert_match subject, issues_text
18
+ end
19
+ end
20
+
21
+ def test_issues_size
22
+ assert_equal '4', @liquid_render.render('{{ issues.size }}')
23
+ end
24
+
25
+ def test_issue_author
26
+ assert_equal @user.name, @liquid_render.render('{{ issue.author.name }}')
27
+ end
28
+
29
+ def test_issue_delegated
30
+ assert_equal [@issue.id, @issue.subject, @issue.description].join('|'),
31
+ @liquid_render.render('{{ issue.id }}|{{ issue.subject }}|{{ issue.description }}')
32
+
33
+ assert_not_equal @issue.subject, @liquid_render.render('{% if issue.closed? %}{{issue.subject}}{% endif %}')
34
+ @issue.closed = true
35
+ assert_equal @issue.subject, @liquid_render.render('{% if issue.closed? %}{{issue.subject}}{% endif %}')
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,38 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class NewsDropTest < ActiveSupport::TestCase
6
+ def setup
7
+ @news = News.first
8
+ @user = User.first
9
+ @liquid_render = LiquidRender.new('user' => Liquid::UserDrop.new(@user),
10
+ 'news' => Liquid::NewsDrop.new(@news),
11
+ 'newss' => Liquid::NewssDrop.new(News.all))
12
+ end
13
+
14
+ def test_newss_all
15
+ newss_text = @liquid_render.render('{% for news in newss.all %} {{news.title }} {% endfor %}')
16
+ News.all.map(&:title).each do |title|
17
+ assert_match title, newss_text
18
+ end
19
+ end
20
+
21
+ def test_newss_last
22
+ assert_equal News.last.title, @liquid_render.render('{{ newss.last.title }}')
23
+ end
24
+
25
+ def test_newss_size
26
+ assert_equal '2', @liquid_render.render('{{ newss.size }}')
27
+ end
28
+
29
+ def test_news_author
30
+ assert_equal @user.name, @liquid_render.render('{{ news.author.name }}')
31
+ end
32
+
33
+ def test_issue_delegated
34
+ assert_equal [@news.id, @news.title, @news.description].join('|'),
35
+ @liquid_render.render('{{ news.id }}|{{ news.title }}|{{ news.description }}')
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,44 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class ProjectsDropTest < ActiveSupport::TestCase
6
+ def setup
7
+ @project = Project.first
8
+ @user = User.first
9
+ @liquid_render = LiquidRender.new('user' => Liquid::UserDrop.new(@user),
10
+ 'project' => Liquid::ProjectDrop.new(@project),
11
+ 'projects' => Liquid::ProjectsDrop.new(Project.all))
12
+ end
13
+
14
+ def test_projects_all
15
+ projects_text = @liquid_render.render('{% for project in projects.all %} {{project.identifier }} {% endfor %}')
16
+ Project.all.map(&:identifier).each do |identifier|
17
+ assert_match identifier, projects_text
18
+ end
19
+ end
20
+
21
+ def test_projects_active
22
+ projects_text = @liquid_render.render('{% for project in projects.active %} {{project.identifier }} {% endfor %}')
23
+ Project.where(:status => 1).map(&:identifier).each do |identifier|
24
+ assert_match identifier, projects_text
25
+ end
26
+ end
27
+
28
+ def test_projects_size
29
+ assert_equal '2', @liquid_render.render('{{ projects.size }}')
30
+ end
31
+
32
+ def test_project_issues
33
+ issues_text = @liquid_render.render('{% for issue in project.issues %} {{issue.subject }} {% endfor %}')
34
+ Project.first.issues.each do |issue|
35
+ assert_match issue.subject, issues_text
36
+ end
37
+ end
38
+
39
+ def test_project_delegated
40
+ assert_equal [@project.id, @project.identifier, @project.description].join('|'),
41
+ @liquid_render.render('{{ project.id }}|{{ project.identifier }}|{{ project.description }}')
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,36 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class UsersDropTest < ActiveSupport::TestCase
6
+ def setup
7
+ @user = User.first
8
+ @liquid_render = LiquidRender.new('user' => Liquid::UserDrop.new(@user),
9
+ 'users' => Liquid::UsersDrop.new(User.all))
10
+ end
11
+
12
+ def test_users_all
13
+ users_text = @liquid_render.render('{% for user in users.all %} {{user.name }} {% endfor %}')
14
+ User.all.map(&:name).each do |name|
15
+ assert_match name, users_text
16
+ end
17
+ end
18
+
19
+ def test_users_current
20
+ assert_equal User.first.name, @liquid_render.render('{{ users.current.name }}')
21
+ end
22
+
23
+ def test_users_size
24
+ assert_equal '3', @liquid_render.render('{{ users.size }}')
25
+ end
26
+
27
+ def test_user_name
28
+ assert_equal @user.name, @liquid_render.render('{{ user.name }}')
29
+ end
30
+
31
+ def test_user_delegated
32
+ assert_equal [@user.name, @user.language].join('|'),
33
+ @liquid_render.render('{{ user.name }}|{{ user.language }}')
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,31 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class ArraysFilterTest < ActiveSupport::TestCase
6
+ def setup
7
+ @liquid_render = LiquidRender.new
8
+ @array = '6,7,8,9,1,2,3,4,5'
9
+ end
10
+
11
+ def test_first_filter
12
+ assert_match '1', @liquid_render.render("{{ '#{@array}' | split: ',' | first: 5 | last }}")
13
+ end
14
+
15
+ def test_sort_filter
16
+ assert_match '123456789', @liquid_render.render("{{ '#{@array}' | split: ',' | sort }}")
17
+ end
18
+
19
+ def test_where_filter
20
+ assert_match '{"name"=>"two", "value"=>5}', @liquid_render.render("{{ objects_arr | where: 'name', 'two' }}")
21
+ assert_match '{"name"=>"one", "value"=>10}', @liquid_render.render("{{ objects_arr | where: 'value', 6, '>' }}")
22
+ assert_match '{"name"=>"one", "value"=>10}', @liquid_render.render("{{ objects_arr | where: 'name', 'on', 'match' }}")
23
+ assert_match '3', @liquid_render.render("{{ objects_arr | where: 'value', '', 'any' | size }}")
24
+ assert_match '1', @liquid_render.render("{{ objects_arr | where: 'value', '', 'none' | size }}")
25
+ assert_match '2', @liquid_render.render("{{ issues.all | where: 'author.name', 'Jonathan', '==' | size }}")
26
+ assert_match '1', @liquid_render.render("{{ issues.all | where: 'author.language', 'CH', '==' | size }}")
27
+ assert_match '0', @liquid_render.render("{{ issues.all | where: 'author.name', '', 'none' | size }}")
28
+ end
29
+
30
+ end
31
+ end
@@ -0,0 +1,67 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class BaseFilterTest < ActiveSupport::TestCase
6
+ def setup
7
+ @liquid_render = LiquidRender.new
8
+ end
9
+
10
+ def test_underscore_filter
11
+ assert_match 'some_text', @liquid_render.render("{{ 'some text' | underscore }}")
12
+ end
13
+
14
+ def test_dasherize_filter
15
+ assert_match 'some-text', @liquid_render.render("{{ 'some text' | dasherize }}")
16
+ end
17
+
18
+ def test_random_filter
19
+ assert @liquid_render.render("{{ random: 10 }}").to_i <= 10
20
+ end
21
+
22
+ def test_encode_filter
23
+ assert_equal 'http%3A%3A%2F%2Fwww.test.com%3Fkey%3Dtest+test+test',
24
+ @liquid_render.render("{{ 'http:://www.test.com?key=test test test' | encode }}")
25
+ end
26
+
27
+ def test_plus_days_filter
28
+ assert_match (Date.today + 3.days).strftime(date_format), @liquid_render.render("{{today | plus_days: 3 | date: '#{date_format}'}}")
29
+ end
30
+
31
+ def test_date_range_filter
32
+ assert_equal '10', @liquid_render.render("{{today | date_range: '#{Date.today - 10.days}'}}")
33
+ end
34
+
35
+ def test_today_filter
36
+ assert_match Date.today.strftime(date_format), @liquid_render.render('{{today}}')
37
+ end
38
+
39
+ def test_utc_filter
40
+ assert_match '2017-01-01 10:13:13 UTC', @liquid_render.render("{{'San, 01 Jan 2017 13:13:13 MSK +03:00' | utc}}")
41
+ end
42
+
43
+ def test_modulo_filter
44
+ assert_equal '3', @liquid_render.render("{{24 | modulo: 7}}")
45
+ end
46
+
47
+ def test_round_filter
48
+ assert_equal '24.12', @liquid_render.render("{{24.12345 | round: 2}}")
49
+ end
50
+
51
+ def test_ceil_filter
52
+ assert_equal '25', @liquid_render.render("{{24.11 | ceil }}")
53
+ end
54
+
55
+ def test_big_decimal_filter_patch
56
+ assert_equal '2.8571', @liquid_render.render("{{ 20 | divided_by: 7.0 | round: 4 }}")
57
+ end
58
+
59
+ def test_floor_filter
60
+ assert_equal '24', @liquid_render.render("{{24.99 | floor }}")
61
+ end
62
+
63
+ def test_currency_filter
64
+ assert_equal '99,99 ₽', @liquid_render.render("{{99.99 | currency: 'RUB' }}")
65
+ end
66
+ end
67
+ end
@@ -0,0 +1,33 @@
1
+ require File.dirname(__FILE__) + '/../liquid_helper'
2
+ include LiquidHelperMethods
3
+
4
+ module Redmineup
5
+ class ColorsFilterTest < ActiveSupport::TestCase
6
+
7
+ def setup
8
+ @liquid_render = LiquidRender.new
9
+ end
10
+
11
+ def test_hex_color
12
+ assert_match '#ff0000', @liquid_render.render("{{ 'red' | hex_color }}")
13
+ end
14
+
15
+ def test_darken_color
16
+ assert_match '#000066', @liquid_render.render("{{ 'blue' | darken_color }}")
17
+ end
18
+
19
+ def test_lighten_color
20
+ assert_match '#9999ff', @liquid_render.render("{{ 'blue' | lighten_color }}")
21
+ end
22
+
23
+ def test_contrasting_text_color
24
+ assert_match '#9999ff', @liquid_render.render("{{ 'blue' | contrasting_text_color }}")
25
+ end
26
+
27
+ def test_convert_to_brightness_value
28
+ assert_match '15', @liquid_render.render("{{ 'blue' | convert_to_brightness_value }}")
29
+ end
30
+
31
+
32
+ end
33
+ end
@@ -0,0 +1,34 @@
1
+ require File.dirname(__FILE__) + '/../test_helper'
2
+
3
+ class LiquidRender
4
+
5
+ def initialize(drops = {})
6
+ @objects_hash = [
7
+ {'name' => 'one', "value" => 10},
8
+ {'name' => 'two', "value" => 5},
9
+ {'name' => 'blank', "value" => nil},
10
+ {'name' => 'three', "value" => 6}
11
+ ]
12
+ @registers = {}
13
+ @assigns = {}
14
+ @assigns['objects_arr'] = @objects_hash
15
+ @assigns['issues'] = Redmineup::Liquid::IssuesDrop.new(Issue.all)
16
+ @assigns['now'] = Time.now
17
+ @assigns['today'] = Date.today.strftime(date_format)
18
+ drops.each do |key, drop|
19
+ @assigns[key] = drop
20
+ end
21
+ end
22
+
23
+ def render(content)
24
+ ::Liquid::Template.parse(content).render(::Liquid::Context.new({}, @assigns, @registers)).html_safe
25
+ rescue => e
26
+ e.message
27
+ end
28
+ end
29
+
30
+ module LiquidHelperMethods
31
+ def date_format
32
+ '%d.%m.%Y'
33
+ end
34
+ end
@@ -0,0 +1,3 @@
1
+ class Attachment < ActiveRecord::Base
2
+ belongs_to :author, :class_name => "User"
3
+ end
@@ -0,0 +1,21 @@
1
+ require_relative 'project'
2
+ require_relative 'user'
3
+
4
+ class Issue < ActiveRecord::Base
5
+ belongs_to :project
6
+ belongs_to :user
7
+ belongs_to :author, class_name: 'User'
8
+
9
+ has_many :relations_from, class_name: 'IssueRelation', foreign_key: 'issue_from_id', dependent: :delete_all
10
+ has_many :relations_to, class_name: 'IssueRelation', foreign_key: 'issue_to_id', dependent: :delete_all
11
+
12
+ up_acts_as_draftable
13
+ up_acts_as_taggable
14
+ up_acts_as_viewed
15
+
16
+ scope :visible, lambda { where('1=1') }
17
+
18
+ def visible?
19
+ true
20
+ end
21
+ end
@@ -0,0 +1,10 @@
1
+ require_relative 'issue'
2
+
3
+ class IssueRelation < ActiveRecord::Base
4
+ belongs_to :issue_from, :class_name => 'Issue'
5
+ belongs_to :issue_to, :class_name => 'Issue'
6
+
7
+ def other_issue(issue)
8
+ (self.issue_from_id == issue.id) ? issue_to : issue_from
9
+ end
10
+ end
@@ -0,0 +1,3 @@
1
+ class News < ActiveRecord::Base
2
+ belongs_to :author, :class_name => 'User'
3
+ end
@@ -0,0 +1,8 @@
1
+ class Project < ActiveRecord::Base
2
+ STATUS_ACTIVE = 1
3
+ has_many :issues, :dependent => :destroy
4
+
5
+ def active?
6
+ status == STATUS_ACTIVE
7
+ end
8
+ end
@@ -0,0 +1,11 @@
1
+ class User < ActiveRecord::Base
2
+ has_many :issues
3
+
4
+ def self.current
5
+ User.first
6
+ end
7
+
8
+ def anonymous?
9
+ false
10
+ end
11
+ end
@@ -0,0 +1,33 @@
1
+ class Voter < ActiveRecord::Base
2
+ up_acts_as_voter
3
+ end
4
+
5
+ class Votable < ActiveRecord::Base
6
+ up_acts_as_votable
7
+ validates_presence_of :name
8
+ end
9
+
10
+ class VotableVoter < ActiveRecord::Base
11
+ up_acts_as_votable
12
+ up_acts_as_voter
13
+ end
14
+
15
+ class StiVotable < ActiveRecord::Base
16
+ up_acts_as_votable
17
+ end
18
+
19
+ class ChildOfStiVotable < StiVotable
20
+ end
21
+
22
+ class StiNotVotable < ActiveRecord::Base
23
+ validates_presence_of :name
24
+ end
25
+
26
+ class VotableChildOfStiNotVotable < StiNotVotable
27
+ up_acts_as_votable
28
+ end
29
+
30
+ class VotableCache < ActiveRecord::Base
31
+ up_acts_as_votable
32
+ validates_presence_of :name
33
+ end
@@ -0,0 +1,12 @@
1
+ require File.dirname(__FILE__) + '/test_helper'
2
+
3
+ class MoneyHelperTest < ActiveSupport::TestCase
4
+ include Redmineup::MoneyHelper
5
+
6
+ def test_price_to_currency
7
+ assert_equal '$3,265.65', price_to_currency(3265.65, 'USD')
8
+ assert_equal '3.265,65 ₽', price_to_currency(3265.65, 'RUB')
9
+ assert_equal '3,200.0', price_to_currency(3200, '')
10
+ assert_equal '3,200.0', price_to_currency(3200, 'Foo')
11
+ end
12
+ end
data/test/schema.rb ADDED
@@ -0,0 +1,144 @@
1
+ ActiveRecord::Schema.define version: 0 do
2
+
3
+ create_table :attachments, force: true do |t|
4
+ t.integer :container_id
5
+ t.string :container_type, limit: 30
6
+ t.string :filename, default: "", null: false
7
+ t.string :disk_filename, default: "", null: false
8
+ t.bigint :filesize, default: 0, null: false
9
+ t.string :content_type, default: ""
10
+ t.string :digest, limit: 64, default: "", null: false
11
+ t.integer :downloads, default: 0, null: false
12
+ t.integer :author_id, default: 0, null: false
13
+ t.timestamp :created_on
14
+ t.string :description
15
+ t.string :disk_directory
16
+ end
17
+
18
+ create_table :drafts, force: true do |t|
19
+ t.string :target_type
20
+ t.integer :target_id
21
+ t.references :project
22
+ t.references :user
23
+ t.references :parent, polymorphic: true
24
+ t.binary :data
25
+ t.datetime :updated_at
26
+ end
27
+
28
+ create_table "tags", :force => true do |t|
29
+ t.column "name", :string
30
+ end
31
+
32
+ create_table "taggings", :force => true do |t|
33
+ t.column "tag_id", :integer
34
+ t.column "taggable_id", :integer
35
+ t.column "taggable_type", :string
36
+ t.column "created_at", :datetime
37
+ end
38
+
39
+ create_table "users", :force => true do |t|
40
+ t.column "name", :string
41
+ t.column "language", :string
42
+ end
43
+
44
+ create_table "issue_relations", :force => true do |t|
45
+ t.column "issue_from_id", :integer
46
+ t.column "issue_to_id", :integer
47
+ t.column "relation_type", :string
48
+ t.column "delay", :integer
49
+ end
50
+
51
+ create_table "issues", :force => true do |t|
52
+ t.integer "project_id"
53
+ t.column "subject", :string
54
+ t.column "description", :string
55
+ t.column "closed", :boolean
56
+ t.column "cached_tag_list", :string
57
+ t.column "user_id", :integer
58
+ t.column "author_id", :integer
59
+ t.column "views", :integer, :default => 0
60
+ t.column "total_views", :integer, :default => 0
61
+ end
62
+
63
+ create_table "votes", :force => true do |t|
64
+ t.references "votable", :polymorphic => true
65
+ t.references "voter", :polymorphic => true
66
+
67
+ t.boolean "vote_flag"
68
+ t.string "vote_scope"
69
+ t.integer "vote_weight"
70
+ t.string "vote_ip"
71
+
72
+ t.timestamps
73
+ end
74
+
75
+ create_table "news", :force => true do |t|
76
+ t.string "title"
77
+ t.text "description"
78
+ t.integer "author_id"
79
+ end
80
+
81
+ create_table "projects", :force => true do |t|
82
+ t.string "name"
83
+ t.text "description"
84
+ t.string "identifier"
85
+ t.integer "status"
86
+ end
87
+
88
+ create_table :voters, :force => true do |t|
89
+ t.string :name
90
+ end
91
+
92
+ create_table :not_voters, :force => true do |t|
93
+ t.string :name
94
+ end
95
+
96
+ create_table :votables, :force => true do |t|
97
+ t.string :name
98
+ end
99
+
100
+ create_table :votable_voters, :force => true do |t|
101
+ t.string :name
102
+ end
103
+
104
+ create_table :sti_votables, :force => true do |t|
105
+ t.string :name
106
+ t.string :type
107
+ end
108
+
109
+ create_table :sti_not_votables, :force => true do |t|
110
+ t.string :name
111
+ t.string :type
112
+ end
113
+
114
+ create_table :not_votables, :force => true do |t|
115
+ t.string :name
116
+ end
117
+
118
+ create_table :votable_caches, :force => true do |t|
119
+ t.string :name
120
+ t.integer :cached_votes_total
121
+ t.integer :cached_votes_score
122
+ t.integer :cached_votes_up
123
+ t.integer :cached_votes_down
124
+ t.integer :cached_weighted_total
125
+ t.integer :cached_weighted_score
126
+ t.float :cached_weighted_average
127
+
128
+ t.integer :cached_scoped_test_votes_total
129
+ t.integer :cached_scoped_test_votes_score
130
+ t.integer :cached_scoped_test_votes_up
131
+ t.integer :cached_scoped_test_votes_down
132
+ t.integer :cached_scoped_weighted_total
133
+ t.integer :cached_scoped_weighted_score
134
+ t.float :cached_scoped_weighted_average
135
+ end
136
+
137
+ create_table :viewings, :force => true do |t|
138
+ t.column :viewer_id, :integer
139
+ t.column :viewed_id, :integer
140
+ t.column :viewed_type, :string
141
+ t.column :ip, :string, :limit => '24'
142
+ t.column :created_at, :datetime
143
+ end
144
+ end