coupler 0.0.1-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (258) hide show
  1. data/.document +5 -0
  2. data/.gitmodules +3 -0
  3. data/.rvmrc +1 -0
  4. data/.vimrc +40 -0
  5. data/Gemfile +27 -0
  6. data/Gemfile.lock +71 -0
  7. data/LICENSE +20 -0
  8. data/NOTES +6 -0
  9. data/README.rdoc +18 -0
  10. data/Rakefile +42 -0
  11. data/TODO +11 -0
  12. data/VERSION +1 -0
  13. data/bin/coupler +7 -0
  14. data/db/.gitignore +6 -0
  15. data/db/migrate/001_initial_schema.rb +166 -0
  16. data/db/migrate/002_stub.rb +4 -0
  17. data/db/migrate/003_stub.rb +4 -0
  18. data/db/migrate/004_create_comparisons.rb +28 -0
  19. data/db/migrate/005_move_database_name.rb +19 -0
  20. data/db/migrate/006_upgrade_comparisons.rb +34 -0
  21. data/db/migrate/007_add_which_to_comparisons.rb +23 -0
  22. data/db/migrate/008_add_result_field_to_transformations.rb +33 -0
  23. data/db/migrate/009_add_generated_flag_to_fields.rb +13 -0
  24. data/db/migrate/010_create_imports.rb +24 -0
  25. data/db/migrate/011_add_primary_key_type.rb +13 -0
  26. data/db/migrate/012_add_transformed_with_to_resources.rb +13 -0
  27. data/db/migrate/013_add_run_count_to_scenarios.rb +13 -0
  28. data/db/migrate/014_add_last_accessed_at_to_some_tables.rb +13 -0
  29. data/db/migrate/015_add_run_number_to_results.rb +15 -0
  30. data/db/migrate/016_fix_scenario_run_count.rb +27 -0
  31. data/db/migrate/017_rename_comparison_columns.rb +14 -0
  32. data/db/migrate/018_fix_scenario_linkage_type.rb +8 -0
  33. data/db/migrate/019_add_columns_to_imports.rb +24 -0
  34. data/db/migrate/020_rename_import_columns.rb +12 -0
  35. data/db/migrate/021_add_fields_to_connections.rb +15 -0
  36. data/db/migrate/022_remove_database_name_from_resources.rb +11 -0
  37. data/features/connections.feature +28 -0
  38. data/features/matchers.feature +35 -0
  39. data/features/projects.feature +11 -0
  40. data/features/resources.feature +62 -0
  41. data/features/scenarios.feature +45 -0
  42. data/features/step_definitions/coupler_steps.rb +145 -0
  43. data/features/step_definitions/matchers_steps.rb +26 -0
  44. data/features/step_definitions/resources_steps.rb +12 -0
  45. data/features/step_definitions/scenarios_steps.rb +7 -0
  46. data/features/step_definitions/transformations_steps.rb +3 -0
  47. data/features/support/env.rb +128 -0
  48. data/features/transformations.feature +22 -0
  49. data/features/wizard.feature +10 -0
  50. data/gfx/coupler-header.svg +213 -0
  51. data/gfx/coupler-sidebar.svg +656 -0
  52. data/gfx/coupler.svg +184 -0
  53. data/gfx/icon.svg +75 -0
  54. data/lib/coupler/base.rb +63 -0
  55. data/lib/coupler/config.rb +128 -0
  56. data/lib/coupler/data_uploader.rb +20 -0
  57. data/lib/coupler/database.rb +31 -0
  58. data/lib/coupler/extensions/connections.rb +57 -0
  59. data/lib/coupler/extensions/exceptions.rb +58 -0
  60. data/lib/coupler/extensions/imports.rb +43 -0
  61. data/lib/coupler/extensions/jobs.rb +21 -0
  62. data/lib/coupler/extensions/matchers.rb +64 -0
  63. data/lib/coupler/extensions/projects.rb +62 -0
  64. data/lib/coupler/extensions/resources.rb +89 -0
  65. data/lib/coupler/extensions/results.rb +100 -0
  66. data/lib/coupler/extensions/scenarios.rb +50 -0
  67. data/lib/coupler/extensions/transformations.rb +70 -0
  68. data/lib/coupler/extensions/transformers.rb +58 -0
  69. data/lib/coupler/extensions.rb +16 -0
  70. data/lib/coupler/helpers.rb +121 -0
  71. data/lib/coupler/import_buffer.rb +48 -0
  72. data/lib/coupler/logger.rb +16 -0
  73. data/lib/coupler/models/common_model.rb +104 -0
  74. data/lib/coupler/models/comparison.rb +166 -0
  75. data/lib/coupler/models/connection.rb +59 -0
  76. data/lib/coupler/models/field.rb +55 -0
  77. data/lib/coupler/models/import.rb +238 -0
  78. data/lib/coupler/models/job.rb +42 -0
  79. data/lib/coupler/models/jobify.rb +17 -0
  80. data/lib/coupler/models/matcher.rb +36 -0
  81. data/lib/coupler/models/project.rb +40 -0
  82. data/lib/coupler/models/resource.rb +287 -0
  83. data/lib/coupler/models/result.rb +92 -0
  84. data/lib/coupler/models/scenario/runner.rb +357 -0
  85. data/lib/coupler/models/scenario.rb +115 -0
  86. data/lib/coupler/models/transformation.rb +117 -0
  87. data/lib/coupler/models/transformer/runner.rb +28 -0
  88. data/lib/coupler/models/transformer.rb +110 -0
  89. data/lib/coupler/models.rb +30 -0
  90. data/lib/coupler/runner.rb +76 -0
  91. data/lib/coupler/scheduler.rb +56 -0
  92. data/lib/coupler.rb +34 -0
  93. data/log/.gitignore +1 -0
  94. data/misc/README +5 -0
  95. data/misc/jruby-json.license +57 -0
  96. data/misc/rack-flash.license +22 -0
  97. data/script/dbconsole.rb +5 -0
  98. data/src/edu/vanderbilt/coupler/Main.java +116 -0
  99. data/src/edu/vanderbilt/coupler/jruby.properties +1 -0
  100. data/tasks/annotations.rake +84 -0
  101. data/tasks/db.rake +120 -0
  102. data/tasks/environment.rake +12 -0
  103. data/tasks/jeweler.rake +43 -0
  104. data/tasks/package.rake +58 -0
  105. data/tasks/rdoc.rake +13 -0
  106. data/tasks/test.rake +63 -0
  107. data/tasks/vendor.rake +43 -0
  108. data/test/README.txt +6 -0
  109. data/test/config.yml +9 -0
  110. data/test/coupler/models/test_import.rb +221 -0
  111. data/test/factories.rb +91 -0
  112. data/test/fixtures/duplicate-keys.csv +5 -0
  113. data/test/fixtures/no-headers.csv +50 -0
  114. data/test/fixtures/people.csv +51 -0
  115. data/test/fixtures/varying-row-size.csv +4 -0
  116. data/test/helper.rb +156 -0
  117. data/test/integration/extensions/test_connections.rb +80 -0
  118. data/test/integration/extensions/test_imports.rb +94 -0
  119. data/test/integration/extensions/test_jobs.rb +52 -0
  120. data/test/integration/extensions/test_matchers.rb +134 -0
  121. data/test/integration/extensions/test_projects.rb +82 -0
  122. data/test/integration/extensions/test_resources.rb +150 -0
  123. data/test/integration/extensions/test_results.rb +89 -0
  124. data/test/integration/extensions/test_scenarios.rb +88 -0
  125. data/test/integration/extensions/test_transformations.rb +113 -0
  126. data/test/integration/extensions/test_transformers.rb +80 -0
  127. data/test/integration/test_field.rb +45 -0
  128. data/test/integration/test_import.rb +78 -0
  129. data/test/integration/test_running_scenarios.rb +379 -0
  130. data/test/integration/test_transformation.rb +56 -0
  131. data/test/integration/test_transforming.rb +154 -0
  132. data/test/table_sets.rb +76 -0
  133. data/test/unit/models/test_common_model.rb +130 -0
  134. data/test/unit/models/test_comparison.rb +619 -0
  135. data/test/unit/models/test_connection.rb +115 -0
  136. data/test/unit/models/test_field.rb +99 -0
  137. data/test/unit/models/test_import.rb +130 -0
  138. data/test/unit/models/test_job.rb +115 -0
  139. data/test/unit/models/test_matcher.rb +82 -0
  140. data/test/unit/models/test_project.rb +102 -0
  141. data/test/unit/models/test_resource.rb +564 -0
  142. data/test/unit/models/test_result.rb +90 -0
  143. data/test/unit/models/test_scenario.rb +199 -0
  144. data/test/unit/models/test_transformation.rb +193 -0
  145. data/test/unit/models/test_transformer.rb +188 -0
  146. data/test/unit/test_base.rb +60 -0
  147. data/test/unit/test_data_uploader.rb +27 -0
  148. data/test/unit/test_database.rb +23 -0
  149. data/test/unit/test_helpers.rb +58 -0
  150. data/test/unit/test_logger.rb +10 -0
  151. data/test/unit/test_models.rb +12 -0
  152. data/test/unit/test_runner.rb +76 -0
  153. data/test/unit/test_scheduler.rb +66 -0
  154. data/uploads/.gitignore +2 -0
  155. data/vendor/java/.gitignore +5 -0
  156. data/webroot/public/css/960.css +1 -0
  157. data/webroot/public/css/dataTables.css +1057 -0
  158. data/webroot/public/css/jquery-ui.css +572 -0
  159. data/webroot/public/css/jquery.treeview.css +68 -0
  160. data/webroot/public/css/reset.css +1 -0
  161. data/webroot/public/css/style.css +504 -0
  162. data/webroot/public/css/text.css +1 -0
  163. data/webroot/public/favicon.ico +0 -0
  164. data/webroot/public/images/12_col.gif +0 -0
  165. data/webroot/public/images/16_col.gif +0 -0
  166. data/webroot/public/images/add.png +0 -0
  167. data/webroot/public/images/ajax-loader.gif +0 -0
  168. data/webroot/public/images/cog.png +0 -0
  169. data/webroot/public/images/coupler.png +0 -0
  170. data/webroot/public/images/foo.png +0 -0
  171. data/webroot/public/images/hammer.png +0 -0
  172. data/webroot/public/images/header.png +0 -0
  173. data/webroot/public/images/home.gif +0 -0
  174. data/webroot/public/images/jobs.gif +0 -0
  175. data/webroot/public/images/sidebar-bottom.png +0 -0
  176. data/webroot/public/images/sidebar.png +0 -0
  177. data/webroot/public/images/treeview-default-line.gif +0 -0
  178. data/webroot/public/images/treeview-default.gif +0 -0
  179. data/webroot/public/images/ui-anim_basic_16x16.gif +0 -0
  180. data/webroot/public/images/ui-bg_flat_0_aaaaaa_40x100.png +0 -0
  181. data/webroot/public/images/ui-bg_flat_75_ffffff_40x100.png +0 -0
  182. data/webroot/public/images/ui-bg_glass_55_fbf9ee_1x400.png +0 -0
  183. data/webroot/public/images/ui-bg_glass_65_ffffff_1x400.png +0 -0
  184. data/webroot/public/images/ui-bg_glass_75_dadada_1x400.png +0 -0
  185. data/webroot/public/images/ui-bg_glass_75_e6e6e6_1x400.png +0 -0
  186. data/webroot/public/images/ui-bg_glass_95_fef1ec_1x400.png +0 -0
  187. data/webroot/public/images/ui-bg_highlight-hard_30_565356_1x100.png +0 -0
  188. data/webroot/public/images/ui-bg_highlight-hard_75_888588_1x100.png +0 -0
  189. data/webroot/public/images/ui-bg_highlight-soft_30_6e3b3a_1x100.png +0 -0
  190. data/webroot/public/images/ui-bg_highlight-soft_35_8e8b8e_1x100.png +0 -0
  191. data/webroot/public/images/ui-bg_highlight-soft_75_cccccc_1x100.png +0 -0
  192. data/webroot/public/images/ui-icons_222222_256x240.png +0 -0
  193. data/webroot/public/images/ui-icons_2e83ff_256x240.png +0 -0
  194. data/webroot/public/images/ui-icons_454545_256x240.png +0 -0
  195. data/webroot/public/images/ui-icons_888888_256x240.png +0 -0
  196. data/webroot/public/images/ui-icons_cd0a0a_256x240.png +0 -0
  197. data/webroot/public/images/ui-icons_ffffff_256x240.png +0 -0
  198. data/webroot/public/js/ajaxupload.js +673 -0
  199. data/webroot/public/js/application.js +40 -0
  200. data/webroot/public/js/jquery-ui.combobox.js +98 -0
  201. data/webroot/public/js/jquery-ui.js +9867 -0
  202. data/webroot/public/js/jquery-ui.min.js +559 -0
  203. data/webroot/public/js/jquery.dataTables.min.js +587 -0
  204. data/webroot/public/js/jquery.min.js +154 -0
  205. data/webroot/public/js/jquery.timeago.js +140 -0
  206. data/webroot/public/js/jquery.tooltip.min.js +19 -0
  207. data/webroot/public/js/jquery.treeview.min.js +15 -0
  208. data/webroot/public/js/resource.js +11 -0
  209. data/webroot/public/js/results.js +56 -0
  210. data/webroot/public/js/transformations.js +95 -0
  211. data/webroot/views/connections/index.erb +5 -0
  212. data/webroot/views/connections/list.erb +34 -0
  213. data/webroot/views/connections/new.erb +55 -0
  214. data/webroot/views/connections/show.erb +36 -0
  215. data/webroot/views/imports/edit.erb +60 -0
  216. data/webroot/views/imports/form.erb +81 -0
  217. data/webroot/views/imports/new.erb +89 -0
  218. data/webroot/views/index.erb +12 -0
  219. data/webroot/views/jobs/index.erb +7 -0
  220. data/webroot/views/jobs/list.erb +24 -0
  221. data/webroot/views/layout.erb +38 -0
  222. data/webroot/views/matchers/form.erb +250 -0
  223. data/webroot/views/matchers/list.erb +32 -0
  224. data/webroot/views/projects/form.erb +14 -0
  225. data/webroot/views/projects/index.erb +96 -0
  226. data/webroot/views/projects/show.erb +24 -0
  227. data/webroot/views/resources/edit.erb +88 -0
  228. data/webroot/views/resources/index.erb +5 -0
  229. data/webroot/views/resources/list.erb +27 -0
  230. data/webroot/views/resources/new.erb +121 -0
  231. data/webroot/views/resources/show.erb +86 -0
  232. data/webroot/views/resources/transform.erb +2 -0
  233. data/webroot/views/results/csv.erb +12 -0
  234. data/webroot/views/results/details.erb +15 -0
  235. data/webroot/views/results/index.erb +2 -0
  236. data/webroot/views/results/list.erb +22 -0
  237. data/webroot/views/results/record.erb +24 -0
  238. data/webroot/views/results/show.erb +68 -0
  239. data/webroot/views/scenarios/index.erb +5 -0
  240. data/webroot/views/scenarios/list.erb +20 -0
  241. data/webroot/views/scenarios/new.erb +99 -0
  242. data/webroot/views/scenarios/run.erb +2 -0
  243. data/webroot/views/scenarios/show.erb +50 -0
  244. data/webroot/views/sidebar.erb +106 -0
  245. data/webroot/views/transformations/create.erb +115 -0
  246. data/webroot/views/transformations/for.erb +16 -0
  247. data/webroot/views/transformations/index.erb +2 -0
  248. data/webroot/views/transformations/list.erb +29 -0
  249. data/webroot/views/transformations/new.erb +126 -0
  250. data/webroot/views/transformations/preview.erb +46 -0
  251. data/webroot/views/transformers/edit.erb +6 -0
  252. data/webroot/views/transformers/form.erb +58 -0
  253. data/webroot/views/transformers/index.erb +2 -0
  254. data/webroot/views/transformers/list.erb +25 -0
  255. data/webroot/views/transformers/new.erb +5 -0
  256. data/webroot/views/transformers/preview.erb +23 -0
  257. data/webroot/views/transformers/show.erb +0 -0
  258. metadata +558 -0
@@ -0,0 +1,50 @@
1
+ 1,David,Garza,31
2
+ 2,Joyce,Burns,42
3
+ 3,Antonio,Rivera,33
4
+ 4,Adam,Medina,47
5
+ 5,Howard,Woods,23
6
+ 6,Frank,Burke,31
7
+ 7,Joseph,Fuller,32
8
+ 8,Bruce,Perry,24
9
+ 9,Judy,Diaz,29
10
+ 10,Diane,Johnston,33
11
+ 11,Michelle,Daniels,35
12
+ 12,Phyllis,Woods,40
13
+ 13,Walter,Morrison,25
14
+ 14,Janet,Webb,46
15
+ 15,Phyllis,Ryan,36
16
+ 16,Susan,Green,21
17
+ 17,Bobby,Rose,31
18
+ 18,Marilyn,Murphy,29
19
+ 19,Martha,Garza,29
20
+ 20,Rebecca,Allen,24
21
+ 21,Sarah,Torres,37
22
+ 22,Martha,Harris,20
23
+ 23,Rachel,Sanders,42
24
+ 24,Rachel,Ross,32
25
+ 25,Joyce,Fox,27
26
+ 26,Angela,Johnson,41
27
+ 27,Lori,Warren,21
28
+ 28,Scott,Alvarez,43
29
+ 29,Christina,Holmes,39
30
+ 30,Keith,Jacobs,27
31
+ 31,Beverly,Stanley,43
32
+ 32,Anna,Tucker,31
33
+ 33,Charles,Wallace,25
34
+ 34,Laura,Rogers,31
35
+ 35,Victor,Holmes,30
36
+ 36,Eric,Bradley,35
37
+ 37,Roger,Little,29
38
+ 38,Cheryl,Edwards,42
39
+ 39,Dennis,Turner,38
40
+ 40,Peter,Thompson,45
41
+ 41,Catherine,Vasquez,46
42
+ 42,Douglas,Mitchell,21
43
+ 43,Lisa,Arnold,40
44
+ 44,Sean,Dean,26
45
+ 45,Julie,Harper,37
46
+ 46,Phyllis,Mason,26
47
+ 47,Jessica,Bryant,26
48
+ 48,Pamela,Stone,30
49
+ 49,Gregory,Brown,43
50
+ 50,Joan,Foster,37
@@ -0,0 +1,51 @@
1
+ id,first_name,last_name,age
2
+ 1,David,Garza,31
3
+ 2,Joyce,Burns,42
4
+ 3,Antonio,Rivera,33
5
+ 4,Adam,Medina,47
6
+ 5,Howard,Woods,23
7
+ 6,Frank,Burke,31
8
+ 7,Joseph,Fuller,32
9
+ 8,Bruce,Perry,24
10
+ 9,Judy,Diaz,29
11
+ 10,Diane,Johnston,33
12
+ 11,Michelle,Daniels,35
13
+ 12,Phyllis,Woods,40
14
+ 13,Walter,Morrison,25
15
+ 14,Janet,Webb,46
16
+ 15,Phyllis,Ryan,36
17
+ 16,Susan,Green,21
18
+ 17,Bobby,Rose,31
19
+ 18,Marilyn,Murphy,29
20
+ 19,Martha,Garza,29
21
+ 20,Rebecca,Allen,24
22
+ 21,Sarah,Torres,37
23
+ 22,Martha,Harris,20
24
+ 23,Rachel,Sanders,42
25
+ 24,Rachel,Ross,32
26
+ 25,Joyce,Fox,27
27
+ 26,Angela,Johnson,41
28
+ 27,Lori,Warren,21
29
+ 28,Scott,Alvarez,43
30
+ 29,Christina,Holmes,39
31
+ 30,Keith,Jacobs,27
32
+ 31,Beverly,Stanley,43
33
+ 32,Anna,Tucker,31
34
+ 33,Charles,Wallace,25
35
+ 34,Laura,Rogers,31
36
+ 35,Victor,Holmes,30
37
+ 36,Eric,Bradley,35
38
+ 37,Roger,Little,29
39
+ 38,Cheryl,Edwards,42
40
+ 39,Dennis,Turner,38
41
+ 40,Peter,Thompson,45
42
+ 41,Catherine,Vasquez,46
43
+ 42,Douglas,Mitchell,21
44
+ 43,Lisa,Arnold,40
45
+ 44,Sean,Dean,26
46
+ 45,Julie,Harper,37
47
+ 46,Phyllis,Mason,26
48
+ 47,Jessica,Bryant,26
49
+ 48,Pamela,Stone,30
50
+ 49,Gregory,Brown,43
51
+ 50,Joan,Foster,37
@@ -0,0 +1,4 @@
1
+ id,foo,bar
2
+ 1,2,3,,,
3
+ 2,3,4,hey
4
+ 3,4,5
data/test/helper.rb ADDED
@@ -0,0 +1,156 @@
1
+ require 'java'
2
+ require 'pp'
3
+
4
+ require 'rubygems'
5
+ require 'bundler'
6
+ Bundler.setup(:default, :development)
7
+
8
+ require 'yaml'
9
+ require 'erb'
10
+ require 'test/unit'
11
+ require 'mocha'
12
+ require 'rack/test'
13
+ require 'rack/flash'
14
+ require 'rack/flash/test'
15
+ require 'nokogiri'
16
+ require 'timecop'
17
+ require 'tempfile'
18
+ require 'tmpdir'
19
+ require 'fileutils'
20
+ require 'table_maker'
21
+ require 'sequel'
22
+ require 'sequel/extensions/schema_dumper'
23
+ require 'forgery'
24
+ require 'ruby-debug'
25
+
26
+ dir = File.dirname(__FILE__)
27
+ $LOAD_PATH.unshift(dir)
28
+ require 'table_sets'
29
+
30
+ $LOAD_PATH.unshift(File.join(dir, '..', 'lib'))
31
+ ENV['COUPLER_ENV'] = 'test'
32
+ require 'coupler'
33
+
34
+ Coupler::Base.set(:sessions, false) # workaround
35
+ Coupler::Base.set(:environment, :test)
36
+ Coupler::Database.instance.migrate!
37
+
38
+ module Coupler
39
+ module Test
40
+ class Base < ::Test::Unit::TestCase
41
+ include Rack::Test::Methods
42
+ @@test_config = YAML.load(ERB.new(File.read(File.join(File.dirname(__FILE__), 'config.yml'))).result(binding))
43
+
44
+ def app
45
+ Coupler::Base
46
+ end
47
+
48
+ def setup
49
+ #@_original_connection_count = connection_count
50
+ @_database = Coupler::Database.instance
51
+ @_database.tables.each do |name|
52
+ next if name == :schema_info
53
+ @_database[name].delete
54
+ end
55
+ end
56
+
57
+ #def run(*args, &block)
58
+ #Sequel::Model.db.transaction do
59
+ #super
60
+ #raise Sequel::Error::Rollback
61
+ #end
62
+ #end
63
+
64
+ def teardown
65
+ if @_tmpdirs
66
+ @_tmpdirs.each { |t| FileUtils.rm_rf(t) }
67
+ end
68
+ # FIXME: this fails a lot, probably for the wrong reason
69
+ #assert_equal @_original_connection_count, connection_count,
70
+ #Sequel::DATABASES.select { |db| db.pool.size > 0 }.collect { |db| db.inspect }.inspect
71
+ end
72
+
73
+ def connection_count
74
+ Sequel::DATABASES.inject(0) { |sum, db| sum + db.pool.size }
75
+ end
76
+
77
+ def make_tmpdir(prefix = 'coupler')
78
+ tmpdir = Dir.mktmpdir(prefix)
79
+ @_tmpdirs ||= []
80
+ @_tmpdirs << tmpdir
81
+ tmpdir
82
+ end
83
+
84
+ def fixture_path(name)
85
+ File.join(File.dirname(__FILE__), "fixtures", name)
86
+ end
87
+
88
+ def fixture_file_upload(name, mime_type = "text/plain")
89
+ file_upload(fixture_path(name), mime_type)
90
+ end
91
+
92
+ def file_upload(file, mime_type = "text/plain")
93
+ Rack::Test::UploadedFile.new(file, mime_type)
94
+ end
95
+
96
+ def fixture_file(name)
97
+ File.open(fixture_path(name))
98
+ end
99
+
100
+ # connection helpers
101
+ def self.each_adapter(&block)
102
+ @@test_config.each_pair { |k, v| block.call(k, v) }
103
+ end
104
+
105
+ def each_adapter(&block)
106
+ self.class.each_adapter(&block)
107
+ end
108
+
109
+ def self.adapter_test(adapter, description, &block)
110
+ test("#{description} for #{adapter} adapter", &block)
111
+ end
112
+
113
+ def self.new_connection(adapter, attribs = {})
114
+ Coupler::Models::Connection.new(
115
+ @@test_config[adapter].merge(:adapter => adapter).update(attribs))
116
+ end
117
+
118
+ def new_connection(*args)
119
+ self.class.new_connection(*args)
120
+ end
121
+ end
122
+
123
+ class UnitTest < Base; end
124
+
125
+ class IntegrationTest < Base
126
+ include Coupler
127
+ include Coupler::Models
128
+ end
129
+ end
130
+ end
131
+
132
+ # deep case equality
133
+ class Hash
134
+ def ===(other)
135
+ if other.is_a?(Hash)
136
+ return false if keys.length != other.keys.length
137
+ all? { |(key, value)| value === other[key] }
138
+ else
139
+ super
140
+ end
141
+ end
142
+ end
143
+
144
+ class Array
145
+ def ===(other)
146
+ if other.is_a?(Array)
147
+ return false if length != other.length
148
+ enum_for(:each_with_index).all? { |value, index| value === other[index] }
149
+ else
150
+ super
151
+ end
152
+ end
153
+ end
154
+
155
+ require 'factory_girl'
156
+ Factory.find_definitions
@@ -0,0 +1,80 @@
1
+ require 'helper'
2
+
3
+ module TestExtensions
4
+ class TestConnections < Coupler::Test::IntegrationTest
5
+ def setup
6
+ super
7
+ @connections = []
8
+ @configs = {}
9
+ each_adapter do |adapter, config|
10
+ conn = new_connection(adapter, :name => "#{adapter} connection").save!
11
+ @connections << conn
12
+ @configs[adapter] = config
13
+ end
14
+ end
15
+
16
+ test "index" do
17
+ get "/connections"
18
+ assert last_response.ok?
19
+ end
20
+
21
+ test "new" do
22
+ get "/connections/new"
23
+ assert last_response.ok?
24
+
25
+ doc = Nokogiri::HTML(last_response.body)
26
+ assert_equal 1, doc.css("form[action='/connections']").length
27
+ assert_equal 1, doc.css("select[name='connection[adapter]']").length
28
+ %w{name host port username password}.each do |name|
29
+ assert_equal 1, doc.css("input[name='connection[#{name}]']").length
30
+ end
31
+ end
32
+
33
+ test "successfully creating connection" do
34
+ attributes = @configs['mysql'].merge(:name => 'foo', :adapter => 'mysql')
35
+ post "/connections", { 'connection' => attributes }
36
+ connection = Connection[:name => 'foo']
37
+ assert connection
38
+
39
+ assert last_response.redirect?, "Wasn't redirected"
40
+ assert_equal "http://example.org/connections", last_response['location']
41
+ end
42
+
43
+ test "successfully creating connection with return to" do
44
+ attributes = @configs['mysql'].merge(:name => 'foo', :adapter => 'mysql')
45
+ post "/connections", { 'connection' => attributes }, { 'rack.session' => { :return_to => '/foo' } }
46
+
47
+ assert last_response.redirect?, "Wasn't redirected"
48
+ assert_equal "http://example.org/foo", last_response['location']
49
+ end
50
+
51
+ test "successfully creating connection with first use" do
52
+ attributes = @configs['mysql'].merge(:name => 'foo', :adapter => 'mysql')
53
+ post "/connections", { 'connection' => attributes }, { 'rack.session' => { :first_use => true } }
54
+
55
+ assert last_response.redirect?, "Wasn't redirected"
56
+ assert_equal "http://example.org/projects/new", last_response['location']
57
+ end
58
+
59
+ test "failing to create connection" do
60
+ attributes = @configs['mysql'].merge(:name => nil, :adapter => 'mysql')
61
+ post "/connections", { 'connection' => attributes }
62
+ assert last_response.ok?
63
+ assert_match /Name is not present/, last_response.body
64
+ end
65
+
66
+ test "show" do
67
+ @connections.each do |conn|
68
+ get "/connections/#{conn.id}"
69
+ assert last_response.ok?
70
+ end
71
+ end
72
+
73
+ test "destroy" do
74
+ delete "/connections/#{@connections[0].id}"
75
+ assert_nil Models::Connection[@connections[0].id]
76
+ assert last_response.redirect?
77
+ assert_equal "http://example.org/connections", last_response['location']
78
+ end
79
+ end
80
+ end
@@ -0,0 +1,94 @@
1
+ require 'helper'
2
+
3
+ module TestExtensions
4
+ class TestImports < Coupler::Test::IntegrationTest
5
+ def setup
6
+ super
7
+ @project = Project.create(:name => 'foo')
8
+ end
9
+
10
+ test "upload saves file" do
11
+ post "/projects/#{@project.id}/imports/upload", :data => fixture_file_upload("people.csv")
12
+ assert last_response.ok?
13
+ end
14
+
15
+ test "upload with no headers" do
16
+ post "/projects/#{@project.id}/imports/upload", :data => fixture_file_upload("no-headers.csv")
17
+ assert last_response.ok?
18
+ end
19
+
20
+ test "create with no issues" do
21
+ cached_import = Import.new(:project => @project, :data => fixture_file_upload('people.csv'))
22
+
23
+ post("/projects/#{@project.id}/imports", {
24
+ :import => {
25
+ :name => cached_import.name,
26
+ :data_cache => cached_import.data_cache,
27
+ :primary_key_name => cached_import.primary_key_name,
28
+ :field_names => cached_import.field_names,
29
+ :field_types => cached_import.field_types,
30
+ :has_headers => true
31
+ }
32
+ })
33
+ assert last_response.redirect?, "Wasn't a redirect"
34
+ assert_match %r{^http://example.org/projects/#{@project[:id]}/resources/\d+$}, last_response['location']
35
+ end
36
+
37
+ test "create with invalid import" do
38
+ cached_import = Import.new(:project => @project, :data => fixture_file_upload('people.csv'))
39
+
40
+ post("/projects/#{@project.id}/imports", {
41
+ :import => {
42
+ :name => cached_import.name,
43
+ :data_cache => cached_import.data_cache,
44
+ :primary_key_name => cached_import.primary_key_name,
45
+ :field_names => nil,
46
+ :field_types => cached_import.field_types,
47
+ :has_headers => true
48
+ }
49
+ })
50
+ assert last_response.ok?
51
+ end
52
+
53
+ test "create with non existant project" do
54
+ post "/projects/8675309/imports"
55
+ assert last_response.redirect?
56
+ assert_equal "http://example.org/projects", last_response['location']
57
+ follow_redirect!
58
+ assert_match /The project you were looking for doesn't exist/, last_response.body
59
+ end
60
+
61
+ test "create with failed import" do
62
+ cached_import = Import.new(:project => @project, :data => fixture_file_upload('duplicate-keys.csv'))
63
+
64
+ post("/projects/#{@project.id}/imports", {
65
+ :import => {
66
+ :name => cached_import.name,
67
+ :data_cache => cached_import.data_cache,
68
+ :primary_key_name => cached_import.primary_key_name,
69
+ :field_names => cached_import.field_names,
70
+ :field_types => cached_import.field_types,
71
+ :has_headers => true
72
+ }
73
+ })
74
+ assert last_response.redirect?, "Wasn't redirected"
75
+ assert_match %r{http://example.org/projects/#{@project.id}/imports/\d+/edit}, last_response['location']
76
+ end
77
+
78
+ test "edit import with duplicate keys" do
79
+ import = Import.create(:project => @project, :data => fixture_file_upload('duplicate-keys.csv'))
80
+ import.import!
81
+ get "/projects/#{@project.id}/imports/#{import.id}/edit"
82
+ assert last_response.ok?
83
+ end
84
+
85
+ test "update import with duplicate keys" do
86
+ import = Import.create(:project => @project, :data => fixture_file_upload('duplicate-keys.csv'))
87
+ import.import!
88
+
89
+ put("/projects/#{@project[:id]}/imports/#{import.id}", { :delete => { "1" => ["1", "2"] }})
90
+ assert last_response.redirect?
91
+ assert_match %r{http://example.org/projects/#{@project[:id]}/resources/\d+}, last_response['location']
92
+ end
93
+ end
94
+ end
@@ -0,0 +1,52 @@
1
+ require 'helper'
2
+
3
+ module TestExtensions
4
+ class TestJobs < Coupler::Test::IntegrationTest
5
+ def self.startup
6
+ super
7
+ conn = new_connection('h2', :name => 'foo')
8
+ conn.database do |db|
9
+ db.create_table!(:foo) do
10
+ primary_key :id
11
+ String :foo
12
+ end
13
+ db[:foo].insert({:foo => 'foo'})
14
+ db[:foo].insert({:foo => 'bar'})
15
+ end
16
+ end
17
+
18
+ def setup
19
+ super
20
+ @connection = new_connection('h2', :name => 'foo').save!
21
+ @project = Project.create!(:name => 'foo')
22
+ @resource = Resource.create!(:name => 'foo', :project => @project, :table_name => 'foo', :connection => @connection)
23
+ @transformer = Transformer.create!(:name => 'foo', :code => 'value', :allowed_types => %w{string}, :result_type => 'string')
24
+ @transformation = Transformation.create!({
25
+ :resource => @resource, :transformer => @transformer,
26
+ :source_field => @resource.fields_dataset[:name => 'foo']
27
+ })
28
+ end
29
+
30
+ test "jobs" do
31
+ job = Job.create!(:name => 'transform', :status => 'scheduled', :resource => @resource)
32
+ get "/jobs"
33
+ assert last_response.ok?
34
+ end
35
+
36
+ test "count" do
37
+ scheduled_job = Job.create!(:name => 'transform', :status => 'scheduled', :resource => @resource)
38
+ completed_job = Job.create!(:name => 'transform', :status => 'done', :resource => @resource, :completed_at => Time.now)
39
+ get "/jobs/count"
40
+ assert last_response.ok?
41
+ assert_equal "1", last_response.body
42
+ end
43
+
44
+ test "progress" do
45
+ job = Job.create!(:name => 'transform', :status => 'scheduled', :resource => @resource, :total => 200, :completed => 54)
46
+ get "/jobs/#{job.id}/progress"
47
+ assert last_response.ok?
48
+ result = JSON.parse(last_response.body)
49
+ assert_equal({'total' => 200, 'completed' => 54}, result)
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,134 @@
1
+ require 'helper'
2
+
3
+ module TestExtensions
4
+ class TestMatchers < Coupler::Test::IntegrationTest
5
+ def self.startup
6
+ super
7
+ conn = new_connection('h2', :name => 'foo')
8
+ conn.database do |db|
9
+ db.create_table!(:foo) do
10
+ primary_key :id
11
+ String :foo
12
+ String :bar
13
+ end
14
+ db[:foo].insert({:foo => 'foo', :bar => 'bar'})
15
+ db[:foo].insert({:foo => 'bar', :bar => 'foo'})
16
+ end
17
+ end
18
+
19
+ def setup
20
+ super
21
+ @connection = new_connection('h2', :name => 'foo').save!
22
+ @project = Project.create!(:name => 'foo')
23
+ @resource = Resource.create!(:name => 'foo', :project => @project, :table_name => 'foo', :connection => @connection)
24
+ @scenario = Scenario.create!(:name => 'foo', :project => @project, :resource_1 => @resource)
25
+ end
26
+
27
+ test "new" do
28
+ get "/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers/new"
29
+ assert last_response.ok?
30
+ end
31
+
32
+ test "new with non existant project" do
33
+ get "/projects/8675309/scenarios/#{@scenario.id}/matchers/new"
34
+ assert last_response.redirect?
35
+ assert_equal "http://example.org/projects", last_response['location']
36
+ follow_redirect!
37
+ assert_match /The project you were looking for doesn't exist/, last_response.body
38
+ end
39
+
40
+ test "new with non existant scenario" do
41
+ get "/projects/#{@project.id}/scenarios/8675309/matchers/new"
42
+ assert last_response.redirect?
43
+ assert_equal "http://example.org/projects/#{@project.id}/scenarios", last_response['location']
44
+ follow_redirect!
45
+ assert_match /The scenario you were looking for doesn't exist/, last_response.body
46
+ end
47
+
48
+ test "successfully creating matcher" do
49
+ field = @resource.fields_dataset[:name => 'foo']
50
+ attribs = {
51
+ 'comparisons_attributes' => {
52
+ '0' => {
53
+ 'lhs_type' => 'field', 'raw_lhs_value' => field.id.to_s,
54
+ 'rhs_type' => 'field', 'raw_rhs_value' => field.id.to_s,
55
+ 'operator' => 'equals'
56
+ }
57
+ }
58
+ }
59
+ post("/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers", { 'matcher' => attribs })
60
+ assert last_response.redirect?, "Wasn't redirected"
61
+ assert_equal "http://example.org/projects/#{@project.id}/scenarios/#{@scenario.id}", last_response['location']
62
+
63
+ assert @scenario.matcher
64
+ end
65
+
66
+ test "edit" do
67
+ field = @resource.fields_dataset[:name => 'foo']
68
+ matcher = Matcher.create!({
69
+ :scenario => @scenario,
70
+ :comparisons_attributes => [{
71
+ 'lhs_type' => 'field', 'raw_lhs_value' => field.id, 'lhs_which' => 1,
72
+ 'rhs_type' => 'field', 'raw_rhs_value' => field.id, 'rhs_which' => 2,
73
+ 'operator' => 'equals'
74
+ }]
75
+ })
76
+ get "/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers/#{matcher.id}/edit"
77
+ assert last_response.ok?
78
+ end
79
+
80
+ test "edit with non existant matcher" do
81
+ get "/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers/8675309/edit"
82
+ assert last_response.redirect?
83
+ assert_equal "http://example.org/projects/#{@project.id}/scenarios/#{@scenario.id}", last_response['location']
84
+ follow_redirect!
85
+ assert_match /The matcher you were looking for doesn't exist/, last_response.body
86
+ end
87
+
88
+ test "updating matcher" do
89
+ foo = @resource.fields_dataset[:name => 'foo']
90
+ bar = @resource.fields_dataset[:name => 'foo']
91
+ matcher = Matcher.create!({
92
+ :scenario => @scenario,
93
+ :comparisons_attributes => [{
94
+ 'lhs_type' => 'field', 'raw_lhs_value' => foo.id, 'lhs_which' => 1,
95
+ 'rhs_type' => 'field', 'raw_rhs_value' => bar.id, 'rhs_which' => 2,
96
+ 'operator' => 'equals'
97
+ }]
98
+ })
99
+ comparison = matcher.comparisons.first
100
+
101
+ attribs = {
102
+ 'comparisons_attributes' => {
103
+ '0' => { 'id' => comparison.id, '_delete' => true },
104
+ '1' => {
105
+ 'lhs_type' => 'field', 'raw_lhs_value' => bar.id.to_s,
106
+ 'rhs_type' => 'field', 'raw_rhs_value' => foo.id.to_s,
107
+ 'operator' => 'equals'
108
+ }
109
+ }
110
+ }
111
+ put "/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers/#{matcher.id}", :matcher => attribs
112
+
113
+ assert last_response.redirect?, "Wasn't redirected"
114
+ assert_equal "http://example.org/projects/#{@project.id}/scenarios/#{@scenario.id}", last_response['location']
115
+ end
116
+
117
+ test "delete" do
118
+ field = @resource.fields_dataset[:name => 'foo']
119
+ matcher = Matcher.create!({
120
+ :scenario => @scenario,
121
+ :comparisons_attributes => [{
122
+ 'lhs_type' => 'field', 'raw_lhs_value' => field.id, 'lhs_which' => 1,
123
+ 'rhs_type' => 'field', 'raw_rhs_value' => field.id, 'rhs_which' => 2,
124
+ 'operator' => 'equals'
125
+ }]
126
+ })
127
+ delete "/projects/#{@project.id}/scenarios/#{@scenario.id}/matchers/#{matcher.id}"
128
+ assert_equal 0, Models::Matcher.filter(:id => matcher.id).count
129
+
130
+ assert last_response.redirect?, "Wasn't redirected"
131
+ assert_equal "http://example.org/projects/#{@project.id}/scenarios/#{@scenario.id}", last_response['location']
132
+ end
133
+ end
134
+ end