picky 2.7.0 → 3.0.0.pre1

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 (213) hide show
  1. data/lib/picky/adapters/rack/base.rb +20 -16
  2. data/lib/picky/adapters/rack/live_parameters.rb +28 -24
  3. data/lib/picky/adapters/rack/search.rb +67 -0
  4. data/lib/picky/adapters/rack.rb +27 -23
  5. data/lib/picky/application.rb +246 -236
  6. data/lib/picky/backend/base.rb +115 -119
  7. data/lib/picky/backend/file/basic.rb +102 -98
  8. data/lib/picky/backend/file/json.rb +27 -23
  9. data/lib/picky/backend/file/marshal.rb +32 -28
  10. data/lib/picky/backend/file/text.rb +45 -41
  11. data/lib/picky/backend/files.rb +19 -15
  12. data/lib/picky/backend/redis/basic.rb +76 -72
  13. data/lib/picky/backend/redis/list_hash.rb +40 -36
  14. data/lib/picky/backend/redis/string_hash.rb +30 -26
  15. data/lib/picky/backend/redis.rb +32 -28
  16. data/lib/picky/bundle.rb +82 -57
  17. data/lib/{bundling.rb → picky/bundling.rb} +0 -0
  18. data/lib/picky/calculations/location.rb +51 -47
  19. data/lib/picky/categories.rb +60 -56
  20. data/lib/picky/categories_indexed.rb +73 -82
  21. data/lib/picky/categories_indexing.rb +12 -8
  22. data/lib/picky/category.rb +109 -120
  23. data/lib/picky/category_indexed.rb +39 -41
  24. data/lib/picky/category_indexing.rb +123 -125
  25. data/lib/picky/character_substituters/west_european.rb +32 -26
  26. data/lib/{constants.rb → picky/constants.rb} +0 -0
  27. data/lib/picky/cores.rb +96 -92
  28. data/lib/{deployment.rb → picky/deployment.rb} +0 -0
  29. data/lib/picky/frontend_adapters/rack.rb +133 -118
  30. data/lib/picky/generators/aliases.rb +5 -3
  31. data/lib/picky/generators/base.rb +11 -7
  32. data/lib/picky/generators/partial/default.rb +7 -3
  33. data/lib/picky/generators/partial/none.rb +24 -20
  34. data/lib/picky/generators/partial/strategy.rb +20 -16
  35. data/lib/picky/generators/partial/substring.rb +94 -90
  36. data/lib/picky/generators/partial_generator.rb +11 -7
  37. data/lib/picky/generators/similarity/default.rb +9 -5
  38. data/lib/picky/generators/similarity/double_metaphone.rb +20 -16
  39. data/lib/picky/generators/similarity/metaphone.rb +20 -16
  40. data/lib/picky/generators/similarity/none.rb +23 -19
  41. data/lib/picky/generators/similarity/phonetic.rb +49 -45
  42. data/lib/picky/generators/similarity/soundex.rb +20 -16
  43. data/lib/picky/generators/similarity/strategy.rb +10 -6
  44. data/lib/picky/generators/similarity_generator.rb +11 -7
  45. data/lib/picky/generators/strategy.rb +14 -10
  46. data/lib/picky/generators/weights/default.rb +9 -5
  47. data/lib/picky/generators/weights/logarithmic.rb +30 -26
  48. data/lib/picky/generators/weights/strategy.rb +10 -6
  49. data/lib/picky/generators/weights_generator.rb +11 -7
  50. data/lib/picky/helpers/measuring.rb +20 -16
  51. data/lib/picky/indexed/bundle/base.rb +39 -37
  52. data/lib/picky/indexed/bundle/memory.rb +68 -64
  53. data/lib/picky/indexed/bundle/redis.rb +73 -69
  54. data/lib/picky/indexed/wrappers/bundle/calculation.rb +26 -22
  55. data/lib/picky/indexed/wrappers/bundle/location.rb +30 -26
  56. data/lib/picky/indexed/wrappers/bundle/wrapper.rb +36 -32
  57. data/lib/picky/indexed/wrappers/category/location.rb +17 -13
  58. data/lib/picky/indexed/wrappers/exact_first.rb +46 -42
  59. data/lib/picky/indexers/base.rb +26 -22
  60. data/lib/picky/indexers/parallel.rb +62 -58
  61. data/lib/picky/indexers/serial.rb +41 -37
  62. data/lib/picky/indexes/index.rb +400 -0
  63. data/lib/picky/indexes/index_indexed.rb +24 -0
  64. data/lib/picky/indexes/index_indexing.rb +138 -0
  65. data/lib/picky/indexes/memory.rb +20 -0
  66. data/lib/picky/indexes/redis.rb +20 -0
  67. data/lib/picky/indexes.rb +68 -61
  68. data/lib/picky/indexes_indexed.rb +16 -12
  69. data/lib/picky/indexes_indexing.rb +41 -37
  70. data/lib/picky/indexing/bundle/base.rb +216 -205
  71. data/lib/picky/indexing/bundle/memory.rb +16 -11
  72. data/lib/picky/indexing/bundle/redis.rb +14 -12
  73. data/lib/picky/indexing/wrappers/category/location.rb +17 -13
  74. data/lib/picky/interfaces/live_parameters.rb +159 -154
  75. data/lib/picky/loader.rb +267 -304
  76. data/lib/picky/loggers/search.rb +20 -13
  77. data/lib/picky/no_source_specified_exception.rb +7 -3
  78. data/lib/picky/performant.rb +6 -2
  79. data/lib/picky/query/allocation.rb +71 -67
  80. data/lib/picky/query/allocations.rb +99 -94
  81. data/lib/picky/query/combination.rb +70 -66
  82. data/lib/picky/query/combinations/base.rb +56 -52
  83. data/lib/picky/query/combinations/memory.rb +36 -32
  84. data/lib/picky/query/combinations/redis.rb +66 -62
  85. data/lib/picky/query/indexes.rb +175 -160
  86. data/lib/picky/query/qualifier_category_mapper.rb +43 -0
  87. data/lib/picky/query/token.rb +165 -172
  88. data/lib/picky/query/tokens.rb +86 -82
  89. data/lib/picky/query/weights.rb +44 -48
  90. data/lib/picky/query.rb +5 -1
  91. data/lib/picky/rack/harakiri.rb +51 -47
  92. data/lib/picky/results.rb +81 -77
  93. data/lib/picky/search.rb +169 -158
  94. data/lib/picky/sinatra.rb +34 -0
  95. data/lib/picky/sources/base.rb +73 -70
  96. data/lib/picky/sources/couch.rb +61 -57
  97. data/lib/picky/sources/csv.rb +68 -64
  98. data/lib/picky/sources/db.rb +139 -135
  99. data/lib/picky/sources/delicious.rb +52 -48
  100. data/lib/picky/sources/mongo.rb +68 -63
  101. data/lib/picky/sources/wrappers/base.rb +20 -16
  102. data/lib/picky/sources/wrappers/location.rb +37 -33
  103. data/lib/picky/statistics.rb +46 -43
  104. data/lib/picky/tasks.rb +3 -0
  105. data/lib/picky/tokenizers/base.rb +192 -187
  106. data/lib/picky/tokenizers/index.rb +25 -21
  107. data/lib/picky/tokenizers/location.rb +33 -29
  108. data/lib/picky/tokenizers/query.rb +49 -43
  109. data/lib/picky.rb +21 -13
  110. data/lib/tasks/application.rake +1 -1
  111. data/lib/tasks/index.rake +3 -3
  112. data/lib/tasks/routes.rake +1 -1
  113. data/lib/tasks/server.rake +1 -1
  114. data/spec/lib/adapters/rack/base_spec.rb +1 -1
  115. data/spec/lib/adapters/rack/live_parameters_spec.rb +1 -1
  116. data/spec/lib/adapters/rack/query_spec.rb +1 -1
  117. data/spec/lib/application_spec.rb +39 -32
  118. data/spec/lib/backend/file/basic_spec.rb +2 -2
  119. data/spec/lib/backend/file/json_spec.rb +2 -2
  120. data/spec/lib/backend/file/marshal_spec.rb +2 -2
  121. data/spec/lib/backend/file/text_spec.rb +1 -1
  122. data/spec/lib/backend/files_spec.rb +14 -24
  123. data/spec/lib/backend/redis/basic_spec.rb +2 -2
  124. data/spec/lib/backend/redis/list_hash_spec.rb +3 -3
  125. data/spec/lib/backend/redis/string_hash_spec.rb +3 -3
  126. data/spec/lib/backend/redis_spec.rb +20 -13
  127. data/spec/lib/calculations/location_spec.rb +1 -1
  128. data/spec/lib/categories_indexed_spec.rb +16 -34
  129. data/spec/lib/category_indexed_spec.rb +9 -27
  130. data/spec/lib/category_indexing_spec.rb +2 -3
  131. data/spec/lib/category_spec.rb +10 -10
  132. data/spec/lib/character_substituters/west_european_spec.rb +6 -5
  133. data/spec/lib/cores_spec.rb +17 -17
  134. data/spec/lib/extensions/symbol_spec.rb +15 -1
  135. data/spec/lib/frontend_adapters/rack_spec.rb +20 -20
  136. data/spec/lib/generators/aliases_spec.rb +3 -3
  137. data/spec/lib/generators/cacher_strategy_spec.rb +1 -1
  138. data/spec/lib/generators/partial/default_spec.rb +3 -3
  139. data/spec/lib/generators/partial/none_spec.rb +2 -2
  140. data/spec/lib/generators/partial/substring_spec.rb +1 -1
  141. data/spec/lib/generators/partial_generator_spec.rb +3 -3
  142. data/spec/lib/generators/similarity/double_metaphone_spec.rb +1 -1
  143. data/spec/lib/generators/similarity/metaphone_spec.rb +1 -1
  144. data/spec/lib/generators/similarity/none_spec.rb +1 -1
  145. data/spec/lib/generators/similarity/phonetic_spec.rb +1 -1
  146. data/spec/lib/generators/similarity/soundex_spec.rb +1 -1
  147. data/spec/lib/generators/similarity_generator_spec.rb +2 -2
  148. data/spec/lib/generators/weights/logarithmic_spec.rb +1 -1
  149. data/spec/lib/generators/weights_generator_spec.rb +1 -1
  150. data/spec/lib/helpers/measuring_spec.rb +2 -2
  151. data/spec/lib/indexed/bundle/memory_spec.rb +6 -6
  152. data/spec/lib/indexed/bundle/redis_spec.rb +4 -4
  153. data/spec/lib/indexed/wrappers/bundle/calculation_spec.rb +2 -3
  154. data/spec/lib/indexed/wrappers/bundle/wrapper_spec.rb +2 -2
  155. data/spec/lib/indexed/wrappers/exact_first_spec.rb +5 -5
  156. data/spec/lib/indexers/base_spec.rb +1 -1
  157. data/spec/lib/indexers/parallel_spec.rb +1 -1
  158. data/spec/lib/indexers/serial_spec.rb +1 -1
  159. data/spec/lib/{index/base_indexed_spec.rb → indexes/index_indexed_spec.rb} +3 -3
  160. data/spec/lib/{index/base_indexing_spec.rb → indexes/index_indexing_spec.rb} +19 -2
  161. data/spec/lib/{index/base_spec.rb → indexes/index_spec.rb} +6 -25
  162. data/spec/lib/{index → indexes}/redis_spec.rb +1 -1
  163. data/spec/lib/indexes_class_spec.rb +2 -2
  164. data/spec/lib/indexes_indexed_spec.rb +1 -1
  165. data/spec/lib/indexes_indexing_spec.rb +1 -1
  166. data/spec/lib/indexes_spec.rb +1 -1
  167. data/spec/lib/indexing/bundle/base_spec.rb +7 -5
  168. data/spec/lib/indexing/bundle/memory_partial_generation_speed_spec.rb +4 -4
  169. data/spec/lib/indexing/bundle/memory_spec.rb +15 -15
  170. data/spec/lib/indexing/bundle/redis_spec.rb +9 -9
  171. data/spec/lib/interfaces/live_parameters_spec.rb +5 -5
  172. data/spec/lib/loader_spec.rb +17 -19
  173. data/spec/lib/loggers/search_spec.rb +2 -2
  174. data/spec/lib/query/allocation_spec.rb +1 -1
  175. data/spec/lib/query/allocations_spec.rb +1 -1
  176. data/spec/lib/query/combination_spec.rb +4 -4
  177. data/spec/lib/query/combinations/base_spec.rb +1 -1
  178. data/spec/lib/query/combinations/memory_spec.rb +1 -1
  179. data/spec/lib/query/combinations/redis_spec.rb +1 -1
  180. data/spec/lib/query/indexes_spec.rb +7 -2
  181. data/spec/lib/query/qualifier_category_mapper_spec.rb +34 -0
  182. data/spec/lib/query/token_spec.rb +32 -53
  183. data/spec/lib/query/tokens_spec.rb +30 -35
  184. data/spec/lib/query/weights_spec.rb +16 -16
  185. data/spec/lib/rack/harakiri_spec.rb +5 -5
  186. data/spec/lib/results_spec.rb +1 -1
  187. data/spec/lib/search_spec.rb +24 -22
  188. data/spec/lib/sinatra_spec.rb +36 -0
  189. data/spec/lib/sources/base_spec.rb +1 -1
  190. data/spec/lib/sources/couch_spec.rb +9 -9
  191. data/spec/lib/sources/csv_spec.rb +7 -7
  192. data/spec/lib/sources/db_spec.rb +2 -2
  193. data/spec/lib/sources/delicious_spec.rb +5 -5
  194. data/spec/lib/sources/mongo_spec.rb +7 -7
  195. data/spec/lib/sources/wrappers/base_spec.rb +2 -2
  196. data/spec/lib/sources/wrappers/location_spec.rb +1 -1
  197. data/spec/lib/statistics_spec.rb +1 -1
  198. data/spec/lib/tokenizers/base_spec.rb +2 -2
  199. data/spec/lib/tokenizers/index_spec.rb +1 -1
  200. data/spec/lib/tokenizers/query_spec.rb +1 -1
  201. metadata +30 -30
  202. data/lib/picky/adapters/rack/query.rb +0 -65
  203. data/lib/picky/index/base.rb +0 -409
  204. data/lib/picky/index/base_indexed.rb +0 -29
  205. data/lib/picky/index/base_indexing.rb +0 -127
  206. data/lib/picky/index/memory.rb +0 -16
  207. data/lib/picky/index/redis.rb +0 -16
  208. data/lib/picky/query/qualifiers.rb +0 -76
  209. data/lib/picky/query/solr.rb +0 -60
  210. data/lib/picky/signals.rb +0 -8
  211. data/lib/picky-tasks.rb +0 -6
  212. data/lib/tasks/spec.rake +0 -11
  213. data/spec/lib/query/qualifiers_spec.rb +0 -31
@@ -1,148 +1,146 @@
1
- #
2
- #
3
- class Category
1
+ module Picky
4
2
 
5
- attr_reader :indexing_exact,
6
- :indexing_partial
7
-
8
- # Prepares and caches this category.
9
3
  #
10
- # This one should be used by users.
11
4
  #
12
- def index
13
- prepare
14
- cache
15
- end
5
+ class Category
16
6
 
17
- # Indexes, creates the "prepared_..." file.
18
- #
19
- def prepare
20
- with_data_snapshot do
21
- indexer.index [self]
7
+ attr_reader :indexing_exact,
8
+ :indexing_partial
9
+
10
+ # Prepares and caches this category.
11
+ #
12
+ # This one should be used by users.
13
+ #
14
+ def index
15
+ prepare
16
+ cache
22
17
  end
23
- end
24
18
 
25
- # Take a data snapshot if the source offers it.
26
- #
27
- def with_data_snapshot
28
- if source.respond_to? :with_snapshot
29
- source.with_snapshot(@index) do
19
+ # Indexes, creates the "prepared_..." file.
20
+ #
21
+ def prepare
22
+ with_data_snapshot do
23
+ indexer.index [self]
24
+ end
25
+ end
26
+
27
+ # Take a data snapshot if the source offers it.
28
+ #
29
+ def with_data_snapshot
30
+ if source.respond_to? :with_snapshot
31
+ source.with_snapshot(@index) do
32
+ yield
33
+ end
34
+ else
30
35
  yield
31
36
  end
32
- else
33
- yield
34
37
  end
35
- end
36
38
 
37
- # Generates all caches for this category.
38
- #
39
- def cache
40
- configure
41
- generate_caches_from_source
42
- generate_partial
43
- generate_caches_from_memory
44
- dump_caches
45
- timed_exclaim %Q{"#{identifier}": Caching finished.}
46
- end
47
- # Generate the cache data.
48
- #
49
- def generate_caches_from_source
50
- indexing_exact.generate_caches_from_source
51
- end
52
- def generate_partial
53
- indexing_partial.generate_partial_from indexing_exact.inverted
54
- end
55
- def generate_caches_from_memory
56
- indexing_partial.generate_caches_from_memory
57
- end
58
- def dump_caches
59
- indexing_exact.dump
60
- indexing_partial.dump
61
- end
39
+ # Generates all caches for this category.
40
+ #
41
+ def cache
42
+ generate_caches_from_source
43
+ generate_partial
44
+ generate_caches_from_memory
45
+ dump_caches
46
+ timed_exclaim %Q{"#{identifier}": Caching finished.}
47
+ end
48
+ # Generate the cache data.
49
+ #
50
+ def generate_caches_from_source
51
+ indexing_exact.generate_caches_from_source
52
+ end
53
+ def generate_partial
54
+ indexing_partial.generate_partial_from indexing_exact.inverted
55
+ end
56
+ def generate_caches_from_memory
57
+ indexing_partial.generate_caches_from_memory
58
+ end
59
+ def dump_caches
60
+ indexing_exact.dump
61
+ indexing_partial.dump
62
+ end
62
63
 
63
- # Return an appropriate source.
64
- #
65
- # If we have no explicit source, we'll check the index for one.
66
- #
67
- def source
68
- @source || @index.source
69
- end
64
+ # Return an appropriate source.
65
+ #
66
+ # If we have no explicit source, we'll check the index for one.
67
+ #
68
+ def source
69
+ (@source && extract_source) || @index.source
70
+ end
71
+ # Extract the actual source if it is wrapped in a time
72
+ # capsule, i.e. a block/lambda.
73
+ #
74
+ # TODO Extract into module.
75
+ #
76
+ def extract_source
77
+ @source = @source.respond_to?(:call) ? @source.call : @source
78
+ end
70
79
 
71
- # Return the key format.
72
- #
73
- # If the source has no key format, then
74
- # check for an explicit key format, and
75
- # if none is defined, ask the index for
76
- # one.
77
- #
78
- def key_format
79
- source.respond_to?(:key_format) && source.key_format || @key_format || @index.key_format
80
- end
80
+ # Return the key format.
81
+ #
82
+ # If the source has no key format, and
83
+ # none is defined on this category, ask
84
+ # the index for one.
85
+ #
86
+ def key_format
87
+ source.respond_to?(:key_format) && source.key_format || @key_format || @index.key_format
88
+ end
81
89
 
82
- # Where the data is taken from.
83
- #
84
- def from
85
- @from || name
86
- end
90
+ # Where the data is taken from.
91
+ #
92
+ def from
93
+ @from || name
94
+ end
87
95
 
88
- # The indexer is lazily generated and cached.
89
- #
90
- # TODO Really cache?
91
- #
92
- def indexer
93
- @indexer ||= source.respond_to?(:each) ? Indexers::Parallel.new(self) : Indexers::Serial.new(self)
94
- end
96
+ # The indexer is lazily generated and cached.
97
+ #
98
+ def indexer
99
+ @indexer ||= source.respond_to?(:each) ? Indexers::Parallel.new(self) : Indexers::Serial.new(self)
100
+ end
95
101
 
96
- # Returns an appropriate tokenizer.
97
- # If one isn't set on this category, will try the index,
98
- # and finally the default index tokenizer.
99
- #
100
- def tokenizer
101
- @tokenizer || @index.tokenizer
102
- end
102
+ # Returns an appropriate tokenizer.
103
+ # If one isn't set on this category, will try the index,
104
+ # and finally the default index tokenizer.
105
+ #
106
+ def tokenizer
107
+ @tokenizer || @index.tokenizer
108
+ end
103
109
 
104
- # We need to set what formatting method should be used.
105
- # Uses the one defined in the indexer.
106
- #
107
- # TODO Make this more dynamic.
108
- #
109
- def configure
110
- indexing_exact[:key_format] = self.key_format
111
- indexing_partial[:key_format] = self.key_format
112
- end
110
+ # Checks the caches for existence.
111
+ #
112
+ def check
113
+ timed_exclaim "Checking #{identifier}."
114
+ indexing_exact.raise_unless_cache_exists
115
+ indexing_partial.raise_unless_cache_exists
116
+ end
113
117
 
114
- # Checks the caches for existence.
115
- #
116
- def check
117
- timed_exclaim "Checking #{identifier}."
118
- indexing_exact.raise_unless_cache_exists
119
- indexing_partial.raise_unless_cache_exists
120
- end
118
+ # Deletes the caches.
119
+ #
120
+ def clear
121
+ timed_exclaim "Deleting #{identifier}."
122
+ indexing_exact.delete
123
+ indexing_partial.delete
124
+ end
121
125
 
122
- # Deletes the caches.
123
- #
124
- def clear
125
- timed_exclaim "Deleting #{identifier}."
126
- indexing_exact.delete
127
- indexing_partial.delete
128
- end
126
+ # Backup the caches.
127
+ # (Revert with restore_caches)
128
+ #
129
+ def backup
130
+ timed_exclaim "Backing up #{identifier}."
131
+ indexing_exact.backup
132
+ indexing_partial.backup
133
+ end
129
134
 
130
- # Backup the caches.
131
- # (Revert with restore_caches)
132
- #
133
- def backup
134
- timed_exclaim "Backing up #{identifier}."
135
- indexing_exact.backup
136
- indexing_partial.backup
137
- end
135
+ # Restore the caches.
136
+ # (Revert with backup_caches)
137
+ #
138
+ def restore
139
+ timed_exclaim "Restoring #{identifier}."
140
+ indexing_exact.restore
141
+ indexing_partial.restore
142
+ end
138
143
 
139
- # Restore the caches.
140
- # (Revert with backup_caches)
141
- #
142
- def restore
143
- timed_exclaim "Restoring #{identifier}."
144
- indexing_exact.restore
145
- indexing_partial.restore
146
144
  end
147
145
 
148
146
  end
@@ -1,37 +1,43 @@
1
1
  # encoding: utf-8
2
2
  #
3
- module CharacterSubstituters # :nodoc:all
4
- # Substitutes Umlauts like
5
- # ä, ö, ü => ae, oe, ue.
6
- # (and more, see specs)
7
- #
8
- class WestEuropean
9
-
10
- def initialize
11
- @chars = ActiveSupport::Multibyte.proxy_class
12
- end
3
+ module Picky
13
4
 
14
- def to_s
15
- self.class.name
16
- end
5
+ module CharacterSubstituters # :nodoc:all
6
+
7
+ # Substitutes Umlauts like
8
+ # ä, ö, ü => ae, oe, ue.
9
+ # (and more, see specs)
10
+ #
11
+ class WestEuropean
12
+
13
+ def initialize
14
+ @chars = ActiveSupport::Multibyte.proxy_class
15
+ end
17
16
 
18
- def substitute text
19
- trans = @chars.new(text).normalize(:kd)
17
+ def to_s
18
+ self.class.name
19
+ end
20
20
 
21
- # substitute special cases
22
- #
23
- trans.gsub!('ß', 'ss')
21
+ def substitute text
22
+ trans = @chars.new(text).normalize(:kd)
24
23
 
25
- # substitute umlauts (of A,O,U,a,o,u)
26
- #
27
- trans.gsub!(/([AOUaou])\314\210/u, '\1e')
24
+ # substitute special cases
25
+ #
26
+ trans.gsub!('ß', 'ss')
27
+
28
+ # substitute umlauts (of A,O,U,a,o,u)
29
+ #
30
+ trans.gsub!(/([AOUaou])\314\210/u, '\1e')
31
+
32
+ # get rid of ecutes, graves and …
33
+ #
34
+ trans.unpack('U*').select { |cp|
35
+ cp < 0x0300 || cp > 0x035F
36
+ }.pack('U*')
37
+ end
28
38
 
29
- # get rid of ecutes, graves and …
30
- #
31
- trans.unpack('U*').select { |cp|
32
- cp < 0x0300 || cp > 0x035F
33
- }.pack('U*')
34
39
  end
35
40
 
36
41
  end
42
+
37
43
  end
File without changes
data/lib/picky/cores.rb CHANGED
@@ -1,104 +1,108 @@
1
- Infinity = 1.0/0
1
+ module Picky
2
2
 
3
- # Handles processing over multiple cores.
4
- #
5
- class Cores # :nodoc:all
6
-
7
- # Pass it an ary or generator.
8
- #
9
- # generator = (1..10).each
10
- # forked generator, :max => 5 do |element|
11
- #
12
- # end
13
- #
14
- # Options include:
15
- # * max: Maximum # of processors to use. Default is all it can get.
3
+ Infinity = 1.0/0
4
+
5
+ # Handles processing over multiple cores.
16
6
  #
17
- def self.forked ary_or_generator, options = {}
18
- return if ary_or_generator.empty?
19
- raise "Block argument needed when running Cores.forked" unless block_given?
20
-
21
- ary_or_generator = ary_or_generator.sort_by { rand } if options[:randomly]
22
- generator = ary_or_generator.each
23
-
24
- # Get the maximum number of processors.
7
+ class Cores # :nodoc:all
8
+
9
+ # Pass it an ary or generator.
25
10
  #
26
- max = max_processors options
27
- currently_processing = 0
28
-
29
- #
11
+ # generator = (1..10).each
12
+ # forked generator, :max => 5 do |element|
30
13
  #
31
- loop do
32
- # Ramp it up to num processors.
14
+ # end
15
+ #
16
+ # Options include:
17
+ # * max: Maximum # of processors to use. Default is all it can get.
18
+ #
19
+ def self.forked ary_or_generator, options = {}
20
+ return if ary_or_generator.empty?
21
+ raise "Block argument needed when running Cores.forked" unless block_given?
22
+
23
+ ary_or_generator = ary_or_generator.sort_by { rand } if options[:randomly]
24
+ generator = ary_or_generator.each
25
+
26
+ # Get the maximum number of processors.
27
+ #
28
+ max = max_processors options
29
+ currently_processing = 0
30
+
33
31
  #
34
- while currently_processing < max
35
-
36
- currently_processing = currently_processing + 1
37
-
38
- element = nil
32
+ #
33
+ loop do
34
+ # Ramp it up to num processors.
35
+ #
36
+ while currently_processing < max
37
+
38
+ currently_processing = currently_processing + 1
39
+
40
+ element = nil
41
+ begin
42
+ element = generator.next
43
+ rescue StopIteration => si
44
+ break
45
+ end
46
+ break unless element
47
+
48
+ Process.fork do
49
+ sleep 0.01*currently_processing
50
+ yield element
51
+ end
52
+
53
+ end
54
+
39
55
  begin
40
- element = generator.next
41
- rescue StopIteration => si
56
+ Process.wait 0 # Block and wait for any child to finish.
57
+ rescue Errno::ECHILD => e
42
58
  break
59
+ ensure
60
+ currently_processing = currently_processing - 1
43
61
  end
44
- break unless element
45
-
46
- Process.fork do
47
- sleep 0.01*currently_processing
48
- yield element
49
- end
50
-
51
- end
52
-
53
- begin
54
- Process.wait 0 # Block and wait for any child to finish.
55
- rescue Errno::ECHILD => e
56
- break
57
- ensure
58
- currently_processing = currently_processing - 1
59
62
  end
60
63
  end
64
+
65
+ # Return the number of maximum usable processors.
66
+ #
67
+ def self.max_processors options = {}
68
+ options[:amount] || [number_of_cores, (options[:max] || Infinity)].min
69
+ end
70
+
71
+ # Gets the number of cores depending on OS.
72
+ #
73
+ def self.number_of_cores
74
+ extract_cores_for actual_platform
75
+ end
76
+ # Extracts the platform os from the platform.
77
+ #
78
+ # Note: Could also use 'rbconfig'.
79
+ #
80
+ def self.actual_platform
81
+ matched = platform.match(/-\b([a-z]*)/)
82
+ matched && matched[1]
83
+ end
84
+ # Returns a mapping
85
+ # os_name => lambda_which_returns_a_number_of_cores
86
+ #
87
+ @@number_of_cores = {
88
+ 'darwin' => lambda { `system_profiler SPHardwareDataType | grep -i 'Total Number Of Cores'`.gsub(/[^\d]/, '') },
89
+ 'linux' => lambda { `grep -ci ^processor /proc/cpuinfo` }
90
+ }
91
+ def self.os_to_core_mapping
92
+ @@number_of_cores
93
+ end
94
+ # Extracts the number of cores for the given os name.
95
+ #
96
+ # Note: Default is 1.
97
+ #
98
+ def self.extract_cores_for os
99
+ code_to_execute = os_to_core_mapping[os]
100
+ code_to_execute && code_to_execute.call.to_i || 1
101
+ end
102
+ def self.platform
103
+ RUBY_PLATFORM
104
+ end
105
+
61
106
  end
62
-
63
- # Return the number of maximum usable processors.
64
- #
65
- def self.max_processors options = {}
66
- options[:amount] || [number_of_cores, (options[:max] || Infinity)].min
67
- end
68
-
69
- # Gets the number of cores depending on OS.
70
- #
71
- def self.number_of_cores
72
- extract_cores_for actual_platform
73
- end
74
- # Extracts the platform os from the platform.
75
- #
76
- # Note: Could also use 'rbconfig'.
77
- #
78
- def self.actual_platform
79
- matched = platform.match(/-\b([a-z]*)/)
80
- matched && matched[1]
81
- end
82
- # Returns a mapping
83
- # os_name => lambda_which_returns_a_number_of_cores
84
- #
85
- @@number_of_cores = {
86
- 'darwin' => lambda { `system_profiler SPHardwareDataType | grep -i 'Total Number Of Cores'`.gsub(/[^\d]/, '') },
87
- 'linux' => lambda { `grep -ci ^processor /proc/cpuinfo` }
88
- }
89
- def self.os_to_core_mapping
90
- @@number_of_cores
91
- end
92
- # Extracts the number of cores for the given os name.
93
- #
94
- # Note: Default is 1.
95
- #
96
- def self.extract_cores_for os
97
- code_to_execute = os_to_core_mapping[os]
98
- code_to_execute && code_to_execute.call.to_i || 1
99
- end
100
- def self.platform
101
- RUBY_PLATFORM
102
- end
103
-
107
+
104
108
  end
File without changes