chewy 0.8.4 → 5.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (303) hide show
  1. checksums.yaml +5 -5
  2. data/.gitignore +1 -0
  3. data/.rubocop.yml +56 -0
  4. data/.rubocop_todo.yml +44 -0
  5. data/.travis.yml +36 -67
  6. data/.yardopts +5 -0
  7. data/Appraisals +63 -58
  8. data/CHANGELOG.md +168 -11
  9. data/Gemfile +16 -9
  10. data/Guardfile +5 -5
  11. data/LEGACY_DSL.md +497 -0
  12. data/README.md +403 -470
  13. data/Rakefile +11 -1
  14. data/chewy.gemspec +12 -15
  15. data/gemfiles/rails.4.0.activerecord.gemfile +9 -9
  16. data/gemfiles/rails.4.1.activerecord.gemfile +9 -9
  17. data/gemfiles/rails.4.2.activerecord.gemfile +8 -8
  18. data/gemfiles/rails.4.2.mongoid.5.2.gemfile +16 -0
  19. data/gemfiles/rails.5.0.activerecord.gemfile +16 -0
  20. data/gemfiles/rails.5.0.mongoid.6.1.gemfile +16 -0
  21. data/gemfiles/rails.5.1.activerecord.gemfile +16 -0
  22. data/gemfiles/rails.5.1.mongoid.6.3.gemfile +16 -0
  23. data/gemfiles/rails.5.2.activerecord.gemfile +16 -0
  24. data/gemfiles/sequel.4.45.gemfile +11 -0
  25. data/lib/chewy/backports/deep_dup.rb +1 -1
  26. data/lib/chewy/backports/duplicable.rb +1 -0
  27. data/lib/chewy/config.rb +53 -21
  28. data/lib/chewy/errors.rb +6 -6
  29. data/lib/chewy/fields/base.rb +59 -29
  30. data/lib/chewy/fields/root.rb +49 -14
  31. data/lib/chewy/index/actions.rb +95 -36
  32. data/lib/chewy/index/aliases.rb +2 -1
  33. data/lib/chewy/index/settings.rb +10 -5
  34. data/lib/chewy/index/specification.rb +60 -0
  35. data/lib/chewy/index.rb +239 -138
  36. data/lib/chewy/journal.rb +55 -0
  37. data/lib/chewy/log_subscriber.rb +8 -8
  38. data/lib/chewy/minitest/helpers.rb +77 -0
  39. data/lib/chewy/minitest/search_index_receiver.rb +80 -0
  40. data/lib/chewy/minitest.rb +1 -0
  41. data/lib/chewy/query/compose.rb +18 -19
  42. data/lib/chewy/query/criteria.rb +34 -24
  43. data/lib/chewy/query/filters.rb +28 -11
  44. data/lib/chewy/query/loading.rb +3 -4
  45. data/lib/chewy/query/nodes/and.rb +1 -1
  46. data/lib/chewy/query/nodes/base.rb +1 -1
  47. data/lib/chewy/query/nodes/bool.rb +6 -4
  48. data/lib/chewy/query/nodes/equal.rb +4 -4
  49. data/lib/chewy/query/nodes/exists.rb +1 -1
  50. data/lib/chewy/query/nodes/expr.rb +2 -2
  51. data/lib/chewy/query/nodes/field.rb +35 -31
  52. data/lib/chewy/query/nodes/has_child.rb +1 -0
  53. data/lib/chewy/query/nodes/has_parent.rb +1 -0
  54. data/lib/chewy/query/nodes/has_relation.rb +10 -12
  55. data/lib/chewy/query/nodes/missing.rb +1 -1
  56. data/lib/chewy/query/nodes/not.rb +1 -1
  57. data/lib/chewy/query/nodes/or.rb +1 -1
  58. data/lib/chewy/query/nodes/prefix.rb +3 -2
  59. data/lib/chewy/query/nodes/query.rb +1 -1
  60. data/lib/chewy/query/nodes/range.rb +9 -9
  61. data/lib/chewy/query/nodes/raw.rb +1 -1
  62. data/lib/chewy/query/nodes/regexp.rb +13 -9
  63. data/lib/chewy/query/nodes/script.rb +4 -4
  64. data/lib/chewy/query/pagination.rb +10 -1
  65. data/lib/chewy/query.rb +286 -170
  66. data/lib/chewy/railtie.rb +7 -6
  67. data/lib/chewy/rake_helper.rb +275 -37
  68. data/lib/chewy/repository.rb +2 -2
  69. data/lib/chewy/rspec/update_index.rb +70 -65
  70. data/lib/chewy/rspec.rb +1 -1
  71. data/lib/chewy/runtime/version.rb +4 -4
  72. data/lib/chewy/search/loader.rb +83 -0
  73. data/lib/chewy/{query → search}/pagination/kaminari.rb +13 -5
  74. data/lib/chewy/search/pagination/will_paginate.rb +43 -0
  75. data/lib/chewy/search/parameters/aggs.rb +16 -0
  76. data/lib/chewy/search/parameters/allow_partial_search_results.rb +27 -0
  77. data/lib/chewy/search/parameters/concerns/bool_storage.rb +24 -0
  78. data/lib/chewy/search/parameters/concerns/hash_storage.rb +23 -0
  79. data/lib/chewy/search/parameters/concerns/integer_storage.rb +14 -0
  80. data/lib/chewy/search/parameters/concerns/query_storage.rb +238 -0
  81. data/lib/chewy/search/parameters/concerns/string_array_storage.rb +23 -0
  82. data/lib/chewy/search/parameters/concerns/string_storage.rb +14 -0
  83. data/lib/chewy/search/parameters/docvalue_fields.rb +12 -0
  84. data/lib/chewy/search/parameters/explain.rb +16 -0
  85. data/lib/chewy/search/parameters/filter.rb +47 -0
  86. data/lib/chewy/search/parameters/highlight.rb +16 -0
  87. data/lib/chewy/search/parameters/indices.rb +123 -0
  88. data/lib/chewy/search/parameters/indices_boost.rb +52 -0
  89. data/lib/chewy/search/parameters/limit.rb +17 -0
  90. data/lib/chewy/search/parameters/load.rb +32 -0
  91. data/lib/chewy/search/parameters/min_score.rb +16 -0
  92. data/lib/chewy/search/parameters/none.rb +27 -0
  93. data/lib/chewy/search/parameters/offset.rb +17 -0
  94. data/lib/chewy/search/parameters/order.rb +64 -0
  95. data/lib/chewy/search/parameters/post_filter.rb +19 -0
  96. data/lib/chewy/search/parameters/preference.rb +16 -0
  97. data/lib/chewy/search/parameters/profile.rb +16 -0
  98. data/lib/chewy/search/parameters/query.rb +19 -0
  99. data/lib/chewy/search/parameters/request_cache.rb +27 -0
  100. data/lib/chewy/search/parameters/rescore.rb +29 -0
  101. data/lib/chewy/search/parameters/script_fields.rb +16 -0
  102. data/lib/chewy/search/parameters/search_after.rb +20 -0
  103. data/lib/chewy/search/parameters/search_type.rb +16 -0
  104. data/lib/chewy/search/parameters/source.rb +73 -0
  105. data/lib/chewy/search/parameters/storage.rb +95 -0
  106. data/lib/chewy/search/parameters/stored_fields.rb +63 -0
  107. data/lib/chewy/search/parameters/suggest.rb +16 -0
  108. data/lib/chewy/search/parameters/terminate_after.rb +16 -0
  109. data/lib/chewy/search/parameters/timeout.rb +16 -0
  110. data/lib/chewy/search/parameters/track_scores.rb +16 -0
  111. data/lib/chewy/search/parameters/types.rb +20 -0
  112. data/lib/chewy/search/parameters/version.rb +16 -0
  113. data/lib/chewy/search/parameters.rb +167 -0
  114. data/lib/chewy/search/query_proxy.rb +257 -0
  115. data/lib/chewy/search/request.rb +1045 -0
  116. data/lib/chewy/search/response.rb +119 -0
  117. data/lib/chewy/search/scoping.rb +50 -0
  118. data/lib/chewy/search/scrolling.rb +134 -0
  119. data/lib/chewy/search.rb +81 -26
  120. data/lib/chewy/stash.rb +79 -0
  121. data/lib/chewy/strategy/active_job.rb +1 -0
  122. data/lib/chewy/strategy/atomic.rb +2 -4
  123. data/lib/chewy/strategy/base.rb +4 -4
  124. data/lib/chewy/strategy/bypass.rb +1 -2
  125. data/lib/chewy/strategy/resque.rb +1 -0
  126. data/lib/chewy/strategy/shoryuken.rb +40 -0
  127. data/lib/chewy/strategy/sidekiq.rb +13 -1
  128. data/lib/chewy/strategy/urgent.rb +1 -1
  129. data/lib/chewy/strategy.rb +19 -10
  130. data/lib/chewy/type/actions.rb +26 -2
  131. data/lib/chewy/type/adapter/active_record.rb +50 -24
  132. data/lib/chewy/type/adapter/base.rb +29 -9
  133. data/lib/chewy/type/adapter/mongoid.rb +19 -10
  134. data/lib/chewy/type/adapter/object.rb +195 -31
  135. data/lib/chewy/type/adapter/orm.rb +69 -33
  136. data/lib/chewy/type/adapter/sequel.rb +37 -19
  137. data/lib/chewy/type/crutch.rb +5 -4
  138. data/lib/chewy/type/import/bulk_builder.rb +122 -0
  139. data/lib/chewy/type/import/bulk_request.rb +78 -0
  140. data/lib/chewy/type/import/journal_builder.rb +45 -0
  141. data/lib/chewy/type/import/routine.rb +138 -0
  142. data/lib/chewy/type/import.rb +150 -176
  143. data/lib/chewy/type/mapping.rb +58 -42
  144. data/lib/chewy/type/observe.rb +21 -15
  145. data/lib/chewy/type/syncer.rb +222 -0
  146. data/lib/chewy/type/witchcraft.rb +89 -34
  147. data/lib/chewy/type/wrapper.rb +48 -16
  148. data/lib/chewy/type.rb +77 -49
  149. data/lib/chewy/version.rb +1 -1
  150. data/lib/chewy.rb +95 -52
  151. data/lib/generators/chewy/install_generator.rb +3 -3
  152. data/lib/sequel/plugins/chewy_observe.rb +4 -19
  153. data/lib/tasks/chewy.rake +91 -28
  154. data/spec/chewy/config_spec.rb +130 -12
  155. data/spec/chewy/fields/base_spec.rb +194 -172
  156. data/spec/chewy/fields/root_spec.rb +123 -17
  157. data/spec/chewy/fields/time_fields_spec.rb +10 -9
  158. data/spec/chewy/index/actions_spec.rb +228 -43
  159. data/spec/chewy/index/aliases_spec.rb +2 -2
  160. data/spec/chewy/index/settings_spec.rb +100 -49
  161. data/spec/chewy/index/specification_spec.rb +169 -0
  162. data/spec/chewy/index_spec.rb +159 -63
  163. data/spec/chewy/journal_spec.rb +268 -0
  164. data/spec/chewy/minitest/helpers_spec.rb +90 -0
  165. data/spec/chewy/minitest/search_index_receiver_spec.rb +120 -0
  166. data/spec/chewy/query/criteria_spec.rb +503 -236
  167. data/spec/chewy/query/filters_spec.rb +96 -68
  168. data/spec/chewy/query/loading_spec.rb +80 -42
  169. data/spec/chewy/query/nodes/and_spec.rb +3 -7
  170. data/spec/chewy/query/nodes/bool_spec.rb +5 -13
  171. data/spec/chewy/query/nodes/equal_spec.rb +20 -20
  172. data/spec/chewy/query/nodes/exists_spec.rb +7 -7
  173. data/spec/chewy/query/nodes/has_child_spec.rb +42 -23
  174. data/spec/chewy/query/nodes/has_parent_spec.rb +42 -23
  175. data/spec/chewy/query/nodes/match_all_spec.rb +2 -2
  176. data/spec/chewy/query/nodes/missing_spec.rb +6 -5
  177. data/spec/chewy/query/nodes/not_spec.rb +5 -7
  178. data/spec/chewy/query/nodes/or_spec.rb +3 -7
  179. data/spec/chewy/query/nodes/prefix_spec.rb +6 -6
  180. data/spec/chewy/query/nodes/query_spec.rb +3 -3
  181. data/spec/chewy/query/nodes/range_spec.rb +19 -19
  182. data/spec/chewy/query/nodes/raw_spec.rb +2 -2
  183. data/spec/chewy/query/nodes/regexp_spec.rb +31 -19
  184. data/spec/chewy/query/nodes/script_spec.rb +5 -5
  185. data/spec/chewy/query/pagination/kaminari_spec.rb +3 -55
  186. data/spec/chewy/query/pagination/will_paginate_spec.rb +5 -0
  187. data/spec/chewy/query/pagination_spec.rb +25 -22
  188. data/spec/chewy/query_spec.rb +510 -505
  189. data/spec/chewy/rake_helper_spec.rb +381 -0
  190. data/spec/chewy/repository_spec.rb +8 -8
  191. data/spec/chewy/rspec/update_index_spec.rb +215 -113
  192. data/spec/chewy/runtime_spec.rb +2 -2
  193. data/spec/chewy/search/loader_spec.rb +117 -0
  194. data/spec/chewy/search/pagination/kaminari_examples.rb +71 -0
  195. data/spec/chewy/search/pagination/kaminari_spec.rb +21 -0
  196. data/spec/chewy/search/pagination/will_paginate_examples.rb +63 -0
  197. data/spec/chewy/search/pagination/will_paginate_spec.rb +23 -0
  198. data/spec/chewy/search/parameters/aggs_spec.rb +5 -0
  199. data/spec/chewy/search/parameters/bool_storage_examples.rb +53 -0
  200. data/spec/chewy/search/parameters/docvalue_fields_spec.rb +5 -0
  201. data/spec/chewy/search/parameters/explain_spec.rb +5 -0
  202. data/spec/chewy/search/parameters/filter_spec.rb +5 -0
  203. data/spec/chewy/search/parameters/hash_storage_examples.rb +59 -0
  204. data/spec/chewy/search/parameters/highlight_spec.rb +5 -0
  205. data/spec/chewy/search/parameters/indices_spec.rb +191 -0
  206. data/spec/chewy/search/parameters/integer_storage_examples.rb +32 -0
  207. data/spec/chewy/search/parameters/limit_spec.rb +5 -0
  208. data/spec/chewy/search/parameters/load_spec.rb +60 -0
  209. data/spec/chewy/search/parameters/min_score_spec.rb +32 -0
  210. data/spec/chewy/search/parameters/none_spec.rb +5 -0
  211. data/spec/chewy/search/parameters/offset_spec.rb +5 -0
  212. data/spec/chewy/search/parameters/order_spec.rb +65 -0
  213. data/spec/chewy/search/parameters/post_filter_spec.rb +5 -0
  214. data/spec/chewy/search/parameters/preference_spec.rb +5 -0
  215. data/spec/chewy/search/parameters/profile_spec.rb +5 -0
  216. data/spec/chewy/search/parameters/query_spec.rb +5 -0
  217. data/spec/chewy/search/parameters/query_storage_examples.rb +388 -0
  218. data/spec/chewy/search/parameters/request_cache_spec.rb +67 -0
  219. data/spec/chewy/search/parameters/rescore_spec.rb +62 -0
  220. data/spec/chewy/search/parameters/script_fields_spec.rb +5 -0
  221. data/spec/chewy/search/parameters/search_after_spec.rb +32 -0
  222. data/spec/chewy/search/parameters/search_type_spec.rb +5 -0
  223. data/spec/chewy/search/parameters/source_spec.rb +156 -0
  224. data/spec/chewy/search/parameters/storage_spec.rb +60 -0
  225. data/spec/chewy/search/parameters/stored_fields_spec.rb +126 -0
  226. data/spec/chewy/search/parameters/string_array_storage_examples.rb +63 -0
  227. data/spec/chewy/search/parameters/string_storage_examples.rb +32 -0
  228. data/spec/chewy/search/parameters/suggest_spec.rb +5 -0
  229. data/spec/chewy/search/parameters/terminate_after_spec.rb +5 -0
  230. data/spec/chewy/search/parameters/timeout_spec.rb +5 -0
  231. data/spec/chewy/search/parameters/track_scores_spec.rb +5 -0
  232. data/spec/chewy/search/parameters/types_spec.rb +5 -0
  233. data/spec/chewy/search/parameters/version_spec.rb +5 -0
  234. data/spec/chewy/search/parameters_spec.rb +145 -0
  235. data/spec/chewy/search/query_proxy_spec.rb +68 -0
  236. data/spec/chewy/search/request_spec.rb +685 -0
  237. data/spec/chewy/search/response_spec.rb +192 -0
  238. data/spec/chewy/search/scrolling_spec.rb +169 -0
  239. data/spec/chewy/search_spec.rb +37 -20
  240. data/spec/chewy/stash_spec.rb +95 -0
  241. data/spec/chewy/strategy/active_job_spec.rb +8 -2
  242. data/spec/chewy/strategy/atomic_spec.rb +4 -1
  243. data/spec/chewy/strategy/resque_spec.rb +8 -2
  244. data/spec/chewy/strategy/shoryuken_spec.rb +66 -0
  245. data/spec/chewy/strategy/sidekiq_spec.rb +10 -2
  246. data/spec/chewy/strategy_spec.rb +6 -6
  247. data/spec/chewy/type/actions_spec.rb +29 -10
  248. data/spec/chewy/type/adapter/active_record_spec.rb +357 -139
  249. data/spec/chewy/type/adapter/mongoid_spec.rb +220 -101
  250. data/spec/chewy/type/adapter/object_spec.rb +129 -40
  251. data/spec/chewy/type/adapter/sequel_spec.rb +304 -152
  252. data/spec/chewy/type/import/bulk_builder_spec.rb +279 -0
  253. data/spec/chewy/type/import/bulk_request_spec.rb +102 -0
  254. data/spec/chewy/type/import/journal_builder_spec.rb +95 -0
  255. data/spec/chewy/type/import/routine_spec.rb +110 -0
  256. data/spec/chewy/type/import_spec.rb +360 -244
  257. data/spec/chewy/type/mapping_spec.rb +96 -29
  258. data/spec/chewy/type/observe_spec.rb +25 -15
  259. data/spec/chewy/type/syncer_spec.rb +123 -0
  260. data/spec/chewy/type/witchcraft_spec.rb +122 -44
  261. data/spec/chewy/type/wrapper_spec.rb +63 -23
  262. data/spec/chewy/type_spec.rb +32 -10
  263. data/spec/chewy_spec.rb +82 -12
  264. data/spec/spec_helper.rb +16 -2
  265. data/spec/support/active_record.rb +6 -2
  266. data/spec/support/class_helpers.rb +4 -19
  267. data/spec/support/mongoid.rb +17 -5
  268. data/spec/support/sequel.rb +6 -1
  269. metadata +250 -57
  270. data/gemfiles/rails.3.2.activerecord.gemfile +0 -15
  271. data/gemfiles/rails.3.2.activerecord.kaminari.gemfile +0 -14
  272. data/gemfiles/rails.3.2.activerecord.will_paginate.gemfile +0 -14
  273. data/gemfiles/rails.4.0.activerecord.kaminari.gemfile +0 -14
  274. data/gemfiles/rails.4.0.activerecord.will_paginate.gemfile +0 -14
  275. data/gemfiles/rails.4.0.mongoid.4.0.0.gemfile +0 -15
  276. data/gemfiles/rails.4.0.mongoid.4.0.0.kaminari.gemfile +0 -14
  277. data/gemfiles/rails.4.0.mongoid.4.0.0.will_paginate.gemfile +0 -14
  278. data/gemfiles/rails.4.0.mongoid.5.1.0.gemfile +0 -15
  279. data/gemfiles/rails.4.0.mongoid.5.1.0.kaminari.gemfile +0 -14
  280. data/gemfiles/rails.4.0.mongoid.5.1.0.will_paginate.gemfile +0 -14
  281. data/gemfiles/rails.4.1.activerecord.kaminari.gemfile +0 -14
  282. data/gemfiles/rails.4.1.activerecord.will_paginate.gemfile +0 -14
  283. data/gemfiles/rails.4.1.mongoid.4.0.0.gemfile +0 -15
  284. data/gemfiles/rails.4.1.mongoid.4.0.0.kaminari.gemfile +0 -14
  285. data/gemfiles/rails.4.1.mongoid.4.0.0.will_paginate.gemfile +0 -14
  286. data/gemfiles/rails.4.1.mongoid.5.1.0.gemfile +0 -15
  287. data/gemfiles/rails.4.1.mongoid.5.1.0.kaminari.gemfile +0 -14
  288. data/gemfiles/rails.4.1.mongoid.5.1.0.will_paginate.gemfile +0 -14
  289. data/gemfiles/rails.4.2.activerecord.kaminari.gemfile +0 -15
  290. data/gemfiles/rails.4.2.activerecord.will_paginate.gemfile +0 -15
  291. data/gemfiles/rails.4.2.mongoid.4.0.0.gemfile +0 -15
  292. data/gemfiles/rails.4.2.mongoid.4.0.0.kaminari.gemfile +0 -14
  293. data/gemfiles/rails.4.2.mongoid.4.0.0.will_paginate.gemfile +0 -14
  294. data/gemfiles/rails.4.2.mongoid.5.1.0.gemfile +0 -15
  295. data/gemfiles/rails.4.2.mongoid.5.1.0.kaminari.gemfile +0 -14
  296. data/gemfiles/rails.4.2.mongoid.5.1.0.will_paginate.gemfile +0 -14
  297. data/gemfiles/rails.5.0.0.beta3.activerecord.gemfile +0 -16
  298. data/gemfiles/rails.5.0.0.beta3.activerecord.kaminari.gemfile +0 -16
  299. data/gemfiles/rails.5.0.0.beta3.activerecord.will_paginate.gemfile +0 -15
  300. data/gemfiles/sequel.4.31.gemfile +0 -13
  301. data/lib/chewy/query/pagination/will_paginate.rb +0 -27
  302. data/lib/chewy/query/scoping.rb +0 -20
  303. data/spec/chewy/query/pagination/will_paginage_spec.rb +0 -60
@@ -4,27 +4,29 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
4
4
  before do
5
5
  stub_model(:city)
6
6
  stub_model(:country)
7
+ City.many_to_one :country
8
+ Country.one_to_many :cities
7
9
  end
8
10
 
9
11
  describe '#name' do
10
- it { expect( described_class.new(City).name ).to eq 'City' }
11
- it { expect( described_class.new(City.order(:id)).name ).to eq 'City' }
12
- it { expect( described_class.new(City, name: 'town').name ).to eq 'Town' }
12
+ it { expect(described_class.new(City).name).to eq 'City' }
13
+ it { expect(described_class.new(City.order(:id)).name).to eq 'City' }
14
+ it { expect(described_class.new(City, name: 'town').name).to eq 'Town' }
13
15
 
14
16
  context do
15
17
  before { stub_model('namespace/city') }
16
18
 
17
- it { expect( described_class.new(Namespace::City).name ).to eq 'City' }
18
- it { expect( described_class.new(Namespace::City.order(:id)).name ).to eq 'City' }
19
+ it { expect(described_class.new(Namespace::City).name).to eq 'City' }
20
+ it { expect(described_class.new(Namespace::City.order(:id)).name).to eq 'City' }
19
21
  end
20
22
  end
21
23
 
22
24
  describe '#default_scope' do
23
- it { expect( described_class.new(City).default_scope.sql ).to eql City.where(nil).sql }
24
- it { expect( described_class.new(City.order(:id)).default_scope.sql ).to eql City.where(nil).sql }
25
- it { expect( described_class.new(City.limit(10)).default_scope.sql ).to eql City.where(nil).sql }
26
- it { expect( described_class.new(City.offset(10)).default_scope.sql ).to eql City.where(nil).sql }
27
- it { expect( described_class.new(City.where(rating: 10)).default_scope.sql ).to eql City.where(rating: 10).sql }
25
+ it { expect(described_class.new(City).default_scope.sql).to eql City.where(nil).sql }
26
+ it { expect(described_class.new(City.order(:id)).default_scope.sql).to eql City.where(nil).sql }
27
+ it { expect(described_class.new(City.limit(10)).default_scope.sql).to eql City.where(nil).sql }
28
+ it { expect(described_class.new(City.offset(10)).default_scope.sql).to eql City.where(nil).sql }
29
+ it { expect(described_class.new(City.where(rating: 10)).default_scope.sql).to eql City.where(rating: 10).sql }
28
30
  end
29
31
 
30
32
  describe '#type_name' do
@@ -44,17 +46,17 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
44
46
  subject { described_class.new(City) }
45
47
 
46
48
  context do
47
- let!(:cities) { 3.times.map { City.new.save! } }
49
+ let!(:cities) { Array.new(3) { City.new.save! } }
48
50
 
49
- it { expect(subject.identify(City.where(nil)) ).to match_array cities.map(&:id) }
50
- it { expect(subject.identify(cities) ).to eq cities.map(&:id) }
51
- it { expect(subject.identify(cities.first) ).to eq([cities.first.id]) }
52
- it { expect(subject.identify(cities.first(2).map(&:id)) ).to eq cities.first(2).map(&:id) }
51
+ it { expect(subject.identify(City.where(nil))).to match_array cities.map(&:id) }
52
+ it { expect(subject.identify(cities)).to eq cities.map(&:id) }
53
+ it { expect(subject.identify(cities.first)).to eq([cities.first.id]) }
54
+ it { expect(subject.identify(cities.first(2).map(&:id))).to eq cities.first(2).map(&:id) }
53
55
  end
54
56
 
55
57
  context 'custom primary_key' do
56
58
  before { stub_model(:city).set_dataset :rating_cities }
57
- let!(:cities) { 3.times.map { |i| City.create! { |c| c.rating = i } } }
59
+ let!(:cities) { Array.new(3) { |i| City.create! { |c| c.rating = i } } }
58
60
 
59
61
  specify { expect(subject.identify(City.where(nil))).to match_array([0, 1, 2]) }
60
62
  specify { expect(subject.identify(cities)).to eq([0, 1, 2]) }
@@ -71,46 +73,62 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
71
73
  end
72
74
 
73
75
  context do
74
- let!(:cities) { 3.times.map { City.create! } }
75
- let!(:deleted) { 4.times.map { City.create!.tap(&:destroy) } }
76
+ let!(:cities) { Array.new(3) { City.create! } }
77
+ let!(:deleted) { Array.new(4) { City.create!.tap(&:destroy) } }
76
78
  subject { described_class.new(City) }
77
79
 
78
80
  specify { expect(import).to eq([{index: cities}]) }
79
- specify { expect(import nil).to eq([]) }
81
+ specify { expect(import(nil)).to eq([]) }
80
82
 
81
83
  specify { expect(import(City.order(:id))).to eq([{index: cities}]) }
82
- specify { expect(import(City.order(:id), batch_size: 2))
83
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
84
+ specify do
85
+ expect(import(City.order(:id), batch_size: 2))
86
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
87
+ end
84
88
 
85
89
  specify { expect(import(cities)).to eq([{index: cities}]) }
86
- specify { expect(import(cities, batch_size: 2))
87
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
88
- specify { expect(import(cities, deleted))
89
- .to eq([{index: cities}, {delete: deleted}]) }
90
- specify { expect(import(cities, deleted, batch_size: 2)).to eq([
91
- {index: cities.first(2)},
92
- {index: cities.last(1)},
93
- {delete: deleted.first(2)},
94
- {delete: deleted.last(2)}]) }
90
+ specify do
91
+ expect(import(cities, batch_size: 2))
92
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
93
+ end
94
+ specify do
95
+ expect(import(cities, deleted))
96
+ .to eq([{index: cities}, {delete: deleted}])
97
+ end
98
+ specify do
99
+ expect(import(cities, deleted, batch_size: 2)).to eq([
100
+ {index: cities.first(2)},
101
+ {index: cities.last(1)},
102
+ {delete: deleted.first(2)},
103
+ {delete: deleted.last(2)}
104
+ ])
105
+ end
95
106
 
96
107
  specify { expect(import(cities.map(&:id))).to eq([{index: cities}]) }
97
108
  specify { expect(import(deleted.map(&:id))).to eq([{delete: deleted.map(&:id)}]) }
98
- specify { expect(import(cities.map(&:id), batch_size: 2))
99
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
100
- specify { expect(import(cities.map(&:id), deleted.map(&:id)))
101
- .to eq([{index: cities}, {delete: deleted.map(&:id)}]) }
102
- specify { expect(import(cities.map(&:id), deleted.map(&:id), batch_size: 2)).to eq([
103
- {index: cities.first(2)},
104
- {index: cities.last(1)},
105
- {delete: deleted.first(2).map(&:id)},
106
- {delete: deleted.last(2).map(&:id)}]) }
109
+ specify do
110
+ expect(import(cities.map(&:id), batch_size: 2))
111
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
112
+ end
113
+ specify do
114
+ expect(import(cities.map(&:id), deleted.map(&:id)))
115
+ .to eq([{index: cities}, {delete: deleted.map(&:id)}])
116
+ end
117
+ specify do
118
+ expect(import(cities.map(&:id), deleted.map(&:id), batch_size: 2)).to eq([
119
+ {index: cities.first(2)},
120
+ {index: cities.last(1)},
121
+ {delete: deleted.first(2).map(&:id)},
122
+ {delete: deleted.last(2).map(&:id)}
123
+ ])
124
+ end
107
125
 
108
126
  specify { expect(import(cities.first, nil)).to eq([{index: [cities.first]}]) }
109
127
  specify { expect(import(cities.first.id, nil)).to eq([{index: [cities.first]}]) }
110
128
  end
111
129
 
112
- context 'additional delete conitions' do
113
- let!(:cities) { 4.times.map { |i| City.create! rating: i } }
130
+ context 'additional delete conditions' do
131
+ let!(:cities) { Array.new(4) { |i| City.create! rating: i } }
114
132
  before { cities.last(2).map(&:destroy) }
115
133
  subject { described_class.new(City) }
116
134
 
@@ -121,111 +139,164 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
121
139
  end
122
140
  end
123
141
  end
124
- subject { described_class.new(City, delete_if: ->{ delete_already? }) }
125
-
126
- specify { expect(import(City.where(nil))).to eq([
127
- { index: [cities[0]], delete: [cities[1]] }
128
- ]) }
129
- specify { expect(import(cities)).to eq([
130
- { index: [cities[0]], delete: [cities[1]] },
131
- { delete: cities.last(2) }
132
- ]) }
133
- specify { expect(import(cities.map(&:id))).to eq([
134
- { index: [cities[0]], delete: [cities[1]] },
135
- { delete: cities.last(2).map(&:id) }
136
- ]) }
142
+ subject { described_class.new(City, delete_if: -> { delete_already? }) }
143
+
144
+ specify do
145
+ expect(import(City.where(nil))).to eq([
146
+ {index: [cities[0]], delete: [cities[1]]}
147
+ ])
148
+ end
149
+ specify do
150
+ expect(import(cities)).to eq([
151
+ {index: [cities[0]], delete: [cities[1]]},
152
+ {delete: cities.last(2)}
153
+ ])
154
+ end
155
+ specify do
156
+ expect(import(cities.map(&:id))).to eq([
157
+ {index: [cities[0]], delete: [cities[1]]},
158
+ {delete: cities.last(2).map(&:id)}
159
+ ])
160
+ end
137
161
  end
138
162
 
139
163
  context 'custom primary_key' do
140
164
  before { stub_model(:city).set_dataset :rating_cities }
141
- let!(:cities) { 3.times.map { |i| City.create! { |c| c.rating = i + 7 } } }
142
- let!(:deleted) { 3.times.map { |i| City.create! { |c| c.rating = i + 10 }.tap(&:destroy) } }
165
+ let!(:cities) { Array.new(3) { |i| City.create! { |c| c.rating = i + 7 } } }
166
+ let!(:deleted) { Array.new(3) { |i| City.create! { |c| c.rating = i + 10 }.tap(&:destroy) } }
143
167
  subject { described_class.new(City) }
144
168
 
145
169
  specify { expect(import).to eq([{index: cities}]) }
146
170
 
147
171
  specify { expect(import(City.order(:rating))).to eq([{index: cities}]) }
148
- specify { expect(import(City.order(:rating), batch_size: 2))
149
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
172
+ specify do
173
+ expect(import(City.order(:rating), batch_size: 2))
174
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
175
+ end
150
176
 
151
177
  specify { expect(import(cities)).to eq([{index: cities}]) }
152
- specify { expect(import(cities, batch_size: 2))
153
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
154
- specify { expect(import(cities, deleted))
155
- .to eq([{index: cities}, {delete: deleted}]) }
156
- specify { expect(import(cities, deleted, batch_size: 2)).to eq([
157
- {index: cities.first(2)},
158
- {index: cities.last(1)},
159
- {delete: deleted.first(2)},
160
- {delete: deleted.last(1)}]) }
178
+ specify do
179
+ expect(import(cities, batch_size: 2))
180
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
181
+ end
182
+ specify do
183
+ expect(import(cities, deleted))
184
+ .to eq([{index: cities}, {delete: deleted}])
185
+ end
186
+ specify do
187
+ expect(import(cities, deleted, batch_size: 2)).to eq([
188
+ {index: cities.first(2)},
189
+ {index: cities.last(1)},
190
+ {delete: deleted.first(2)},
191
+ {delete: deleted.last(1)}
192
+ ])
193
+ end
161
194
 
162
195
  specify { expect(import(cities.map(&:rating))).to eq([{index: cities}]) }
163
- specify { expect(import(cities.map(&:rating), batch_size: 2))
164
- .to eq([{index: cities.first(2)}, {index: cities.last(1)}]) }
165
- specify { expect(import(cities.map(&:rating), deleted.map(&:rating)))
166
- .to eq([{index: cities}, {delete: deleted.map(&:rating)}]) }
167
- specify { expect(import(cities.map(&:rating), deleted.map(&:rating), batch_size: 2)).to eq([
168
- {index: cities.first(2)},
169
- {index: cities.last(1)},
170
- {delete: deleted.first(2).map(&:rating)},
171
- {delete: deleted.last(1).map(&:rating)}]) }
196
+ specify do
197
+ expect(import(cities.map(&:rating), batch_size: 2))
198
+ .to eq([{index: cities.first(2)}, {index: cities.last(1)}])
199
+ end
200
+ specify do
201
+ expect(import(cities.map(&:rating), deleted.map(&:rating)))
202
+ .to eq([{index: cities}, {delete: deleted.map(&:rating)}])
203
+ end
204
+ specify do
205
+ expect(import(cities.map(&:rating), deleted.map(&:rating), batch_size: 2)).to eq([
206
+ {index: cities.first(2)},
207
+ {index: cities.last(1)},
208
+ {delete: deleted.first(2).map(&:rating)},
209
+ {delete: deleted.last(1).map(&:rating)}
210
+ ])
211
+ end
172
212
  end
173
213
 
174
214
  context 'default scope' do
175
- let!(:cities) { 4.times.map { |i| City.create!(rating: i/3) } }
176
- let!(:deleted) { 3.times.map { |i| City.create!.tap(&:destroy) } }
215
+ let!(:cities) { Array.new(4) { |i| City.create!(rating: i / 3) } }
216
+ let!(:deleted) { Array.new(3) { City.create!.tap(&:destroy) } }
177
217
  subject { described_class.new(City.where(rating: 0)) }
178
218
 
179
219
  specify { expect(import).to eq([{index: cities.first(3)}]) }
180
220
 
181
- specify { expect(import(City.where('rating < 2')))
182
- .to eq([{index: cities.first(3)}]) }
183
- specify { expect(import(City.where('rating < 2'), batch_size: 2))
184
- .to eq([{index: cities.first(2)}, {index: [cities[2]]}]) }
185
- specify { expect(import(City.where('rating < 1')))
186
- .to eq([{index: cities.first(3)}]) }
221
+ specify do
222
+ expect(import(City.where('rating < 2')))
223
+ .to eq([{index: cities.first(3)}])
224
+ end
225
+ specify do
226
+ expect(import(City.where('rating < 2'), batch_size: 2))
227
+ .to eq([{index: cities.first(2)}, {index: [cities[2]]}])
228
+ end
229
+ specify do
230
+ expect(import(City.where('rating < 1')))
231
+ .to eq([{index: cities.first(3)}])
232
+ end
187
233
  specify { expect(import(City.where('rating > 1'))).to eq([]) }
188
234
 
189
- specify { expect(import(cities.first(2)))
190
- .to eq([{index: cities.first(2)}]) }
191
- specify { expect(import(cities))
192
- .to eq([{index: cities.first(3)}, {delete: cities.last(1)}]) }
193
- specify { expect(import(cities, batch_size: 2))
194
- .to eq([{index: cities.first(2)}, {index: [cities[2]]}, {delete: cities.last(1)}]) }
195
- specify { expect(import(cities, deleted))
196
- .to eq([{index: cities.first(3)}, {delete: cities.last(1) + deleted}]) }
197
- specify { expect(import(cities, deleted, batch_size: 3)).to eq([
198
- {index: cities.first(3)},
199
- {delete: cities.last(1) + deleted.first(2)},
200
- {delete: deleted.last(1)}]) }
201
-
202
- specify { expect(import(cities.first(2).map(&:id)))
203
- .to eq([{index: cities.first(2)}]) }
204
- specify { expect(import(cities.map(&:id)))
205
- .to eq([{index: cities.first(3)}, {delete: [cities.last.id]}]) }
206
- specify { expect(import(cities.map(&:id), batch_size: 2))
207
- .to eq([{index: cities.first(2)}, {index: [cities[2]]}, {delete: [cities.last.id]}]) }
208
- specify { expect(import(cities.map(&:id), deleted.map(&:id)))
209
- .to eq([{index: cities.first(3)}, {delete: [cities.last.id] + deleted.map(&:id)}]) }
210
- specify { expect(import(cities.map(&:id), deleted.map(&:id), batch_size: 3)).to eq([
211
- {index: cities.first(3)},
212
- {delete: [cities.last.id] + deleted.first(2).map(&:id)},
213
- {delete: deleted.last(1).map(&:id)}]) }
235
+ specify do
236
+ expect(import(cities.first(2)))
237
+ .to eq([{index: cities.first(2)}])
238
+ end
239
+ specify do
240
+ expect(import(cities))
241
+ .to eq([{index: cities.first(3)}, {delete: cities.last(1)}])
242
+ end
243
+ specify do
244
+ expect(import(cities, batch_size: 2))
245
+ .to eq([{index: cities.first(2)}, {index: [cities[2]]}, {delete: cities.last(1)}])
246
+ end
247
+ specify do
248
+ expect(import(cities, deleted))
249
+ .to eq([{index: cities.first(3)}, {delete: cities.last(1) + deleted}])
250
+ end
251
+ specify do
252
+ expect(import(cities, deleted, batch_size: 3)).to eq([
253
+ {index: cities.first(3)},
254
+ {delete: cities.last(1) + deleted.first(2)},
255
+ {delete: deleted.last(1)}
256
+ ])
257
+ end
258
+
259
+ specify do
260
+ expect(import(cities.first(2).map(&:id)))
261
+ .to eq([{index: cities.first(2)}])
262
+ end
263
+ specify do
264
+ expect(import(cities.map(&:id)))
265
+ .to eq([{index: cities.first(3)}, {delete: [cities.last.id]}])
266
+ end
267
+ specify do
268
+ expect(import(cities.map(&:id), batch_size: 2))
269
+ .to eq([{index: cities.first(2)}, {index: [cities[2]]}, {delete: [cities.last.id]}])
270
+ end
271
+ specify do
272
+ expect(import(cities.map(&:id), deleted.map(&:id)))
273
+ .to eq([{index: cities.first(3)}, {delete: [cities.last.id] + deleted.map(&:id)}])
274
+ end
275
+ specify do
276
+ expect(import(cities.map(&:id), deleted.map(&:id), batch_size: 3)).to eq([
277
+ {index: cities.first(3)},
278
+ {delete: [cities.last.id] + deleted.first(2).map(&:id)},
279
+ {delete: deleted.last(1).map(&:id)}
280
+ ])
281
+ end
214
282
  end
215
283
 
216
284
  context 'error handling' do
217
- let!(:cities) { 3.times.map { |i| City.create! } }
218
- let!(:deleted) { 2.times.map { |i| City.create!.tap(&:destroy) } }
285
+ let!(:cities) { Array.new(3) { City.create! } }
286
+ let!(:deleted) { Array.new(2) { City.create!.tap(&:destroy) } }
219
287
  let(:ids) { (cities + deleted).map(&:id) }
220
288
  subject { described_class.new(City) }
221
289
 
222
290
  let(:data_comparer) do
223
- ->(id, data) { objects = data[:index] || data[:delete]; !objects.map { |o| o.respond_to?(:id) ? o.id : o }.include?(id) }
291
+ lambda do |id, data|
292
+ objects = data[:index] || data[:delete]
293
+ !objects.map { |o| o.respond_to?(:id) ? o.id : o }.include?(id)
294
+ end
224
295
  end
225
296
 
226
297
  context 'implicit scope' do
227
- specify { expect(subject.import { |data| true }).to eq(true) }
228
- specify { expect(subject.import { |data| false }).to eq(false) }
298
+ specify { expect(subject.import { |_data| true }).to eq(true) }
299
+ specify { expect(subject.import { |_data| false }).to eq(false) }
229
300
  specify { expect(subject.import(batch_size: 1, &data_comparer.curry[cities[0].id])).to eq(false) }
230
301
  specify { expect(subject.import(batch_size: 1, &data_comparer.curry[cities[1].id])).to eq(false) }
231
302
  specify { expect(subject.import(batch_size: 1, &data_comparer.curry[cities[2].id])).to eq(false) }
@@ -236,8 +307,8 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
236
307
  context 'explicit scope' do
237
308
  let(:scope) { City.where(id: ids) }
238
309
 
239
- specify { expect(subject.import(scope) { |data| true }).to eq(true) }
240
- specify { expect(subject.import(scope) { |data| false }).to eq(false) }
310
+ specify { expect(subject.import(scope) { |_data| true }).to eq(true) }
311
+ specify { expect(subject.import(scope) { |_data| false }).to eq(false) }
241
312
  specify { expect(subject.import(scope, batch_size: 1, &data_comparer.curry[cities[0].id])).to eq(false) }
242
313
  specify { expect(subject.import(scope, batch_size: 1, &data_comparer.curry[cities[1].id])).to eq(false) }
243
314
  specify { expect(subject.import(scope, batch_size: 1, &data_comparer.curry[cities[2].id])).to eq(false) }
@@ -246,8 +317,8 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
246
317
  end
247
318
 
248
319
  context 'objects' do
249
- specify { expect(subject.import(cities + deleted) { |data| true }).to eq(true) }
250
- specify { expect(subject.import(cities + deleted) { |data| false }).to eq(false) }
320
+ specify { expect(subject.import(cities + deleted) { |_data| true }).to eq(true) }
321
+ specify { expect(subject.import(cities + deleted) { |_data| false }).to eq(false) }
251
322
  specify { expect(subject.import(cities + deleted, batch_size: 1, &data_comparer.curry[cities[0].id])).to eq(false) }
252
323
  specify { expect(subject.import(cities + deleted, batch_size: 1, &data_comparer.curry[cities[1].id])).to eq(false) }
253
324
  specify { expect(subject.import(cities + deleted, batch_size: 1, &data_comparer.curry[cities[2].id])).to eq(false) }
@@ -256,8 +327,8 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
256
327
  end
257
328
 
258
329
  context 'ids' do
259
- specify { expect(subject.import(ids) { |data| true }).to eq(true) }
260
- specify { expect(subject.import(ids) { |data| false }).to eq(false) }
330
+ specify { expect(subject.import(ids) { |_data| true }).to eq(true) }
331
+ specify { expect(subject.import(ids) { |_data| false }).to eq(false) }
261
332
  specify { expect(subject.import(ids, batch_size: 1, &data_comparer.curry[cities[0].id])).to eq(false) }
262
333
  specify { expect(subject.import(ids, batch_size: 1, &data_comparer.curry[cities[1].id])).to eq(false) }
263
334
  specify { expect(subject.import(ids, batch_size: 1, &data_comparer.curry[cities[2].id])).to eq(false) }
@@ -267,54 +338,135 @@ describe Chewy::Type::Adapter::Sequel, :sequel do
267
338
  end
268
339
  end
269
340
 
341
+ describe '#import_fields' do
342
+ subject { described_class.new(Country) }
343
+ let!(:countries) { Array.new(3) { |i| Country.create!(rating: i) { |c| c.id = i + 1 } } }
344
+ let!(:cities) { Array.new(6) { |i| City.create!(rating: i + 3, country_id: (i + 4) / 2) { |c| c.id = i + 3 } } }
345
+
346
+ specify { expect(subject.import_fields).to match([contain_exactly(1, 2, 3)]) }
347
+ specify { expect(subject.import_fields(fields: [:rating])).to match([contain_exactly([1, 0], [2, 1], [3, 2])]) }
348
+
349
+ context 'scopes' do
350
+ context do
351
+ subject { described_class.new(Country.eager_graph(:cities)) }
352
+
353
+ specify { expect(subject.import_fields).to match([contain_exactly(1, 2, 3)]) }
354
+ specify { expect(subject.import_fields(fields: [:rating])).to match([contain_exactly([1, 0], [2, 1], [3, 2])]) }
355
+ end
356
+
357
+ context do
358
+ subject { described_class.new(Country.eager(:cities)) }
359
+
360
+ specify { expect(subject.import_fields).to match([contain_exactly(1, 2, 3)]) }
361
+ specify { expect(subject.import_fields(fields: [:rating])).to match([contain_exactly([1, 0], [2, 1], [3, 2])]) }
362
+ end
363
+
364
+ context do
365
+ subject { described_class.new(Country.join(:cities, country_id: :id)) }
366
+
367
+ specify { expect(subject.import_fields).to match([contain_exactly(2, 3)]) }
368
+ specify { expect(subject.import_fields(fields: [:rating])).to match([contain_exactly([2, 1], [3, 2])]) }
369
+ end
370
+
371
+ context 'ignores default scope if another scope is passed' do
372
+ subject { described_class.new(Country.join(:cities, country_id: :id)) }
373
+
374
+ specify { expect(subject.import_fields(Country.where('rating < 2'))).to match([contain_exactly(1, 2)]) }
375
+ specify { expect(subject.import_fields(Country.where('rating < 2'), fields: [:rating])).to match([contain_exactly([1, 0], [2, 1])]) }
376
+ end
377
+ end
378
+
379
+ context 'objects/ids' do
380
+ specify { expect(subject.import_fields(1, 2)).to match([contain_exactly(1, 2)]) }
381
+ specify { expect(subject.import_fields(1, 2, fields: [:rating])).to match([contain_exactly([1, 0], [2, 1])]) }
382
+
383
+ specify { expect(subject.import_fields(countries.first(2))).to match([contain_exactly(1, 2)]) }
384
+ specify { expect(subject.import_fields(countries.first(2), fields: [:rating])).to match([contain_exactly([1, 0], [2, 1])]) }
385
+ end
386
+
387
+ context 'batch_size' do
388
+ specify { expect(subject.import_fields(batch_size: 2)).to match([contain_exactly(1, 2), [3]]) }
389
+ specify { expect(subject.import_fields(batch_size: 2, fields: [:rating])).to match([contain_exactly([1, 0], [2, 1]), [[3, 2]]]) }
390
+
391
+ specify { expect(subject.import_fields(Country.where('rating < 2'), batch_size: 2)).to match([contain_exactly(1, 2)]) }
392
+ specify { expect(subject.import_fields(Country.where('rating < 2'), batch_size: 2, fields: [:rating])).to match([contain_exactly([1, 0], [2, 1])]) }
393
+
394
+ specify { expect(subject.import_fields(1, 2, batch_size: 1)).to match([[1], [2]]) }
395
+ specify { expect(subject.import_fields(1, 2, batch_size: 1, fields: [:rating])).to match([[[1, 0]], [[2, 1]]]) }
396
+
397
+ specify { expect(subject.import_fields(countries.first(2), batch_size: 1)).to match([[1], [2]]) }
398
+ specify { expect(subject.import_fields(countries.first(2), batch_size: 1, fields: [:rating])).to match([[[1, 0]], [[2, 1]]]) }
399
+ end
400
+ end
401
+
270
402
  describe '#load' do
271
403
  context do
272
- let!(:cities) { 3.times.map { |i| City.create!(rating: i/2) } }
273
- let!(:deleted) { 2.times.map { |i| City.create!.tap(&:destroy) } }
404
+ let!(:cities) { Array.new(3) { |i| City.create!(rating: i / 2) } }
405
+ let!(:deleted) { Array.new(2) { City.create!.tap(&:destroy) } }
406
+ let(:city_ids) { cities.map(&:id) }
407
+ let(:deleted_ids) { deleted.map(&:id) }
274
408
 
275
409
  let(:type) { double(type_name: 'user') }
276
410
 
277
411
  subject { described_class.new(City) }
278
412
 
279
- specify { expect(subject.load(cities.map { |c| double(id: c.id) }, _type: type)).to eq(cities) }
280
- specify { expect(subject.load(cities.map { |c| double(id: c.id) }.reverse, _type: type)).to eq(cities.reverse) }
281
- specify { expect(subject.load(deleted.map { |c| double(id: c.id) }, _type: type)).to eq([nil, nil]) }
282
- specify { expect(subject.load((cities + deleted).map { |c| double(id: c.id) }, _type: type)).to eq([*cities, nil, nil]) }
283
- specify { expect(subject.load(cities.map { |c| double(id: c.id) }, _type: type, scope: ->{ where(rating: 0) }))
284
- .to eq(cities.first(2) + [nil]) }
285
- specify { expect(subject.load(cities.map { |c| double(id: c.id) },
286
- _type: type, scope: ->{ where(rating: 0) }, user: {scope: ->{ where(rating: 1)}}))
287
- .to eq([nil, nil] + cities.last(1)) }
288
- xspecify { expect(subject.load(cities.map { |c| double(id: c.id) }, _type: type, scope: City.where(rating: 1)))
289
- .to eq([nil, nil] + cities.last(1)) }
290
- specify { expect(subject.load(cities.map { |c| double(id: c.id) },
291
- _type: type, scope: City.where(rating: 1), user: {scope: ->{ where(rating: 0)}}))
292
- .to eq(cities.first(2) + [nil]) }
413
+ specify { expect(subject.load(city_ids, _type: type)).to eq(cities) }
414
+ specify { expect(subject.load(city_ids.reverse, _type: type)).to eq(cities.reverse) }
415
+ specify { expect(subject.load(deleted_ids, _type: type)).to eq([nil, nil]) }
416
+ specify { expect(subject.load(city_ids + deleted_ids, _type: type)).to eq([*cities, nil, nil]) }
417
+ specify do
418
+ expect(subject.load(city_ids, _type: type, scope: -> { where(rating: 0) }))
419
+ .to eq(cities.first(2) + [nil])
420
+ end
421
+ specify do
422
+ expect(subject.load(city_ids,
423
+ _type: type, scope: -> { where(rating: 0) }, user: {scope: -> { where(rating: 1) }}))
424
+ .to eq([nil, nil] + cities.last(1))
425
+ end
426
+ xspecify 'sequel does not support scopes merge' do
427
+ expect(subject.load(city_ids, _type: type, scope: City.where(rating: 1)))
428
+ .to eq([nil, nil] + cities.last(1))
429
+ end
430
+ specify do
431
+ expect(subject.load(city_ids,
432
+ _type: type, scope: City.where(rating: 1), user: {scope: -> { where(rating: 0) }}))
433
+ .to eq(cities.first(2) + [nil])
434
+ end
293
435
  end
294
436
 
295
437
  context 'custom primary_key' do
296
438
  before { stub_model(:city).set_dataset :rating_cities }
297
- let!(:cities) { 3.times.map { |i| City.create!(country_id: i/2) { |c| c.rating = i + 7 } } }
298
- let!(:deleted) { 2.times.map { |i| City.create! { |c| c.rating = i + 10 }.tap(&:destroy) } }
439
+ let!(:cities) { Array.new(3) { |i| City.create!(country_id: i / 2) { |c| c.rating = i + 7 } } }
440
+ let!(:deleted) { Array.new(2) { |i| City.create! { |c| c.rating = i + 10 }.tap(&:destroy) } }
441
+ let(:city_ids) { cities.map(&:rating) }
442
+ let(:deleted_ids) { deleted.map(&:rating) }
299
443
 
300
444
  let(:type) { double(type_name: 'user') }
301
445
 
302
446
  subject { described_class.new(City) }
303
447
 
304
- specify { expect(subject.load(cities.map { |c| double(rating: c.rating) }, _type: type)).to eq(cities) }
305
- specify { expect(subject.load(cities.map { |c| double(rating: c.rating) }.reverse, _type: type)).to eq(cities.reverse) }
306
- specify { expect(subject.load(deleted.map { |c| double(rating: c.rating) }, _type: type)).to eq([nil, nil]) }
307
- specify { expect(subject.load((cities + deleted).map { |c| double(rating: c.rating) }, _type: type)).to eq([*cities, nil, nil]) }
308
- specify { expect(subject.load(cities.map { |c| double(rating: c.rating) }, _type: type, scope: ->{ where(country_id: 0) }))
309
- .to eq(cities.first(2) + [nil]) }
310
- specify { expect(subject.load(cities.map { |c| double(rating: c.rating) },
311
- _type: type, scope: ->{ where(country_id: 0) }, user: {scope: ->{ where(country_id: 1)}}))
312
- .to eq([nil, nil] + cities.last(1)) }
313
- xspecify { expect(subject.load(cities.map { |c| double(rating: c.rating) }, _type: type, scope: City.where(country_id: 1)))
314
- .to eq([nil, nil] + cities.last(1)) }
315
- specify { expect(subject.load(cities.map { |c| double(rating: c.rating) },
316
- _type: type, scope: City.where(country_id: 1), user: {scope: ->{ where(country_id: 0)}}))
317
- .to eq(cities.first(2) + [nil]) }
448
+ specify { expect(subject.load(city_ids, _type: type)).to eq(cities) }
449
+ specify { expect(subject.load(city_ids.reverse, _type: type)).to eq(cities.reverse) }
450
+ specify { expect(subject.load(deleted_ids, _type: type)).to eq([nil, nil]) }
451
+ specify { expect(subject.load(city_ids + deleted_ids, _type: type)).to eq([*cities, nil, nil]) }
452
+ specify do
453
+ expect(subject.load(city_ids, _type: type, scope: -> { where(country_id: 0) }))
454
+ .to eq(cities.first(2) + [nil])
455
+ end
456
+ specify do
457
+ expect(subject.load(city_ids,
458
+ _type: type, scope: -> { where(country_id: 0) }, user: {scope: -> { where(country_id: 1) }}))
459
+ .to eq([nil, nil] + cities.last(1))
460
+ end
461
+ xspecify 'sequel does not support scopes merge' do
462
+ expect(subject.load(city_ids, _type: type, scope: City.where(country_id: 1)))
463
+ .to eq([nil, nil] + cities.last(1))
464
+ end
465
+ specify do
466
+ expect(subject.load(city_ids,
467
+ _type: type, scope: City.where(country_id: 1), user: {scope: -> { where(country_id: 0) }}))
468
+ .to eq(cities.first(2) + [nil])
469
+ end
318
470
  end
319
471
  end
320
472
  end