redcar 0.9.2 → 0.10

Sign up to get free protection for your applications and to get access to all the features.
Files changed (234) hide show
  1. data/CHANGES +34 -4
  2. data/Rakefile +2 -1
  3. data/lib/redcar.rb +3 -3
  4. data/lib/redcar/installer.rb +2 -3
  5. data/plugins/application/features/step_definitions/dialog_steps.rb +7 -0
  6. data/plugins/application/features/step_definitions/key_steps.rb +18 -0
  7. data/plugins/application/features/step_definitions/menu_steps.rb +5 -6
  8. data/plugins/application/features/step_definitions/speedbar_steps.rb +29 -9
  9. data/plugins/application/features/step_definitions/tree_steps.rb +13 -0
  10. data/plugins/application/features/support/env.rb +39 -5
  11. data/plugins/application/features/support/fake_event.rb +12 -0
  12. data/plugins/application/lib/application.rb +5 -6
  13. data/plugins/application/lib/application/dialog.rb +53 -10
  14. data/plugins/application/lib/application/dialogs/modeless_list_dialog.rb +85 -0
  15. data/plugins/application/lib/application/keymap.rb +10 -8
  16. data/plugins/application/lib/application/menu.rb +38 -16
  17. data/plugins/application/lib/application/treebook.rb +30 -0
  18. data/plugins/application/lib/application/window.rb +20 -2
  19. data/plugins/application/spec/application/command/executor_spec.rb +1 -0
  20. data/plugins/application/spec/application/menu_spec.rb +26 -26
  21. data/plugins/application/spec/application/treebook_spec.rb +6 -6
  22. data/plugins/application/spec/spec_helper.rb +10 -1
  23. data/plugins/application_swt/lib/application_swt.rb +25 -3
  24. data/plugins/application_swt/lib/application_swt/dialog_adapter.rb +48 -27
  25. data/plugins/application_swt/lib/application_swt/dialogs/filter_list_dialog_controller.rb +22 -11
  26. data/plugins/application_swt/lib/application_swt/dialogs/modeless_dialog.rb +113 -0
  27. data/plugins/application_swt/lib/application_swt/dialogs/modeless_html_dialog.rb +85 -0
  28. data/plugins/application_swt/lib/application_swt/dialogs/modeless_list_dialog_controller.rb +143 -0
  29. data/plugins/application_swt/lib/application_swt/gradient.rb +61 -0
  30. data/plugins/application_swt/lib/application_swt/menu/binding_translator.rb +4 -4
  31. data/plugins/application_swt/lib/application_swt/notebook.rb +5 -8
  32. data/plugins/application_swt/lib/application_swt/speedbar.rb +1 -0
  33. data/plugins/application_swt/lib/application_swt/treebook.rb +6 -8
  34. data/plugins/application_swt/lib/application_swt/window.rb +85 -57
  35. data/plugins/application_swt/lib/swt/graphics_utils.rb +23 -0
  36. data/plugins/application_swt/lib/swt/vtab_folder.rb +7 -0
  37. data/plugins/application_swt/lib/swt/vtab_label.rb +1 -1
  38. data/plugins/application_swt/spec/application_swt/gradient_spec.rb +142 -0
  39. data/plugins/auto_completer/lib/auto_completer.rb +10 -42
  40. data/plugins/auto_completer/lib/auto_completer/list_dialog.rb +21 -0
  41. data/plugins/clojure/lib/clojure.rb +33 -0
  42. data/plugins/{repl/lib/repl/clojure_mirror.rb → clojure/lib/clojure/repl_mirror.rb} +16 -20
  43. data/plugins/clojure/plugin.rb +9 -0
  44. data/plugins/{repl/spec/repl/clojure_mirror_spec.rb → clojure/spec/clojure/repl_mirror_spec.rb} +12 -13
  45. data/plugins/clojure/spec/spec_helper.rb +5 -0
  46. data/plugins/{repl → clojure}/vendor/Wrapper.clj +0 -0
  47. data/plugins/{repl → clojure}/vendor/dummy +0 -0
  48. data/plugins/{repl → clojure}/vendor/enclojure-wrapper.jar +0 -0
  49. data/plugins/connection_manager/lib/connection_manager.rb +13 -13
  50. data/plugins/declarations/lib/declarations.rb +17 -6
  51. data/plugins/document_search/features/find.feature +389 -0
  52. data/plugins/document_search/features/find_and_replace.feature +723 -0
  53. data/plugins/document_search/features/replace.feature +69 -62
  54. data/plugins/document_search/lib/document_search.rb +81 -64
  55. data/plugins/document_search/lib/document_search/commands.rb +258 -0
  56. data/plugins/document_search/lib/document_search/find_and_replace_speedbar.rb +142 -0
  57. data/plugins/document_search/lib/document_search/find_speedbar.rb +102 -0
  58. data/plugins/document_search/lib/document_search/query_options.rb +45 -0
  59. data/plugins/edit_view/features/case_change.feature +9 -5
  60. data/plugins/edit_view/features/step_definitions/editing_steps.rb +19 -0
  61. data/plugins/edit_view/lib/edit_view.rb +15 -12
  62. data/plugins/edit_view/lib/edit_view/actions/arrow_keys.rb +12 -2
  63. data/plugins/edit_view/lib/edit_view/commands/text_conversion_commands.rb +1 -1
  64. data/plugins/edit_view/lib/edit_view/document.rb +129 -99
  65. data/plugins/edit_view_swt/lib/edit_view_swt.rb +33 -15
  66. data/plugins/encryption/encryption.rb +2 -0
  67. data/plugins/find-in-project/lib/find_in_project.rb +3 -5
  68. data/plugins/find-in-project/lib/find_in_project/views/index.html.erb +2 -0
  69. data/plugins/groovy/features/step_definitions/groovy_steps.rb +2 -2
  70. data/plugins/groovy/features/syntax_check_groovy.feature +3 -3
  71. data/plugins/groovy/lib/groovy.rb +38 -0
  72. data/plugins/groovy/lib/groovy/commands.rb +10 -0
  73. data/plugins/{repl/lib/repl/groovy_mirror.rb → groovy/lib/groovy/repl_mirror.rb} +33 -13
  74. data/plugins/groovy/lib/{syntax_check/groovy.rb → groovy/syntax_checker.rb} +13 -8
  75. data/plugins/groovy/plugin.rb +5 -4
  76. data/plugins/{repl/spec/repl/groovy_mirror_spec.rb → groovy/spec/groovy/repl_mirror_spec.rb} +14 -13
  77. data/plugins/groovy/spec/spec_helper.rb +5 -0
  78. data/plugins/html_view/assets/json2.js +476 -0
  79. data/plugins/html_view/lib/html_view.rb +1 -0
  80. data/plugins/java/features/fixtures/test.java +0 -0
  81. data/plugins/java/features/support/env.rb +27 -0
  82. data/plugins/java/features/syntax_check_java.feature +86 -0
  83. data/plugins/java/lib/syntax_check/java.rb +86 -0
  84. data/plugins/java/plugin.rb +7 -0
  85. data/plugins/javascript/features/fixtures/test2.js +5 -0
  86. data/plugins/javascript/features/step_definitions/javascript_steps.rb +16 -0
  87. data/plugins/javascript/features/support/env.rb +14 -0
  88. data/plugins/javascript/features/syntax_check_javascript.feature +46 -3
  89. data/plugins/javascript/lib/syntax_check/javascript.rb +15 -9
  90. data/plugins/line_tools/features/trim_line.feature +49 -0
  91. data/plugins/line_tools/lib/line_tools.rb +5 -1
  92. data/plugins/mirah/README +7 -0
  93. data/plugins/mirah/features/fixtures/test.mirah +2 -0
  94. data/plugins/mirah/features/syntax_check_mirah.feature +46 -0
  95. data/plugins/mirah/lib/mirah.rb +43 -0
  96. data/plugins/mirah/lib/mirah/my_error_handler.rb +22 -0
  97. data/plugins/mirah/lib/mirah/repl_mirror.rb +50 -0
  98. data/plugins/mirah/lib/mirah/syntax_checker.rb +38 -0
  99. data/plugins/mirah/plugin.rb +8 -0
  100. data/plugins/mirah/spec/mirah/repl_mirror_spec.rb +188 -0
  101. data/plugins/mirah/spec/spec_helper.rb +5 -0
  102. data/plugins/mirah/vendor/mirah-parser.jar +0 -0
  103. data/plugins/pair_highlighter/lib/pair_highlighter/document_controller.rb +24 -23
  104. data/plugins/plugin_manager_ui/lib/plugin_manager_ui.rb +10 -1
  105. data/plugins/plugin_manager_ui/views/index.html.erb +2 -0
  106. data/plugins/project/features/find_file.feature +40 -16
  107. data/plugins/project/features/highlight_focussed_tab.feature +16 -10
  108. data/plugins/project/features/step_definitions/find_file_steps.rb +11 -0
  109. data/plugins/project/features/step_definitions/project_tree_steps.rb +5 -1
  110. data/plugins/project/features/support/env.rb +5 -0
  111. data/plugins/project/lib/project/commands.rb +8 -1
  112. data/plugins/project/lib/project/dir_controller.rb +4 -1
  113. data/plugins/project/lib/project/find_file_dialog.rb +16 -12
  114. data/plugins/project/lib/project/manager.rb +30 -1
  115. data/plugins/project_search/vendor/lucene/CHANGELOG +147 -0
  116. data/plugins/project_search/vendor/lucene/CONTRIBUTORS +17 -0
  117. data/plugins/project_search/vendor/lucene/Gemfile +9 -0
  118. data/plugins/project_search/vendor/lucene/Gemfile.lock +33 -0
  119. data/plugins/project_search/vendor/lucene/LICENSE +19 -0
  120. data/plugins/project_search/vendor/lucene/README.rdoc +283 -0
  121. data/plugins/project_search/vendor/lucene/Rakefile +35 -0
  122. data/plugins/project_search/vendor/lucene/examples/active_model/serializers.rb +25 -0
  123. data/plugins/project_search/vendor/lucene/examples/active_model/validation.rb +26 -0
  124. data/plugins/project_search/vendor/lucene/examples/admin/Rakefile +4 -0
  125. data/plugins/project_search/vendor/lucene/examples/admin/admin.rb +29 -0
  126. data/plugins/project_search/vendor/lucene/examples/admin/public/jquery.js +4376 -0
  127. data/plugins/project_search/vendor/lucene/examples/admin/public/neo4j.css +153 -0
  128. data/plugins/project_search/vendor/lucene/examples/admin/public/neo_admin.js +18 -0
  129. data/plugins/project_search/vendor/lucene/examples/admin/spec/admin_spec.rb +26 -0
  130. data/plugins/project_search/vendor/lucene/examples/admin/views/index.erb +21 -0
  131. data/plugins/project_search/vendor/lucene/examples/filetree/README.rdoc +9 -0
  132. data/plugins/project_search/vendor/lucene/examples/filetree/app.rb +7 -0
  133. data/plugins/project_search/vendor/lucene/examples/filetree/batch.props +5 -0
  134. data/plugins/project_search/vendor/lucene/examples/filetree/features/step_definitions/add_steps.rb +121 -0
  135. data/plugins/project_search/vendor/lucene/examples/filetree/features/support/env.rb +30 -0
  136. data/plugins/project_search/vendor/lucene/examples/filetree/features/support/rspec_helper.rb +50 -0
  137. data/plugins/project_search/vendor/lucene/examples/filetree/features/treesizes.feature +19 -0
  138. data/plugins/project_search/vendor/lucene/examples/imdb/1_create_neo_db.rb +66 -0
  139. data/plugins/project_search/vendor/lucene/examples/imdb/2_index_db.rb +23 -0
  140. data/plugins/project_search/vendor/lucene/examples/imdb/README +12 -0
  141. data/plugins/project_search/vendor/lucene/examples/imdb/find_actors.rb +56 -0
  142. data/plugins/project_search/vendor/lucene/examples/imdb/install.sh +12 -0
  143. data/plugins/project_search/vendor/lucene/examples/imdb/model.rb +37 -0
  144. data/plugins/project_search/vendor/lucene/examples/railway/README +111 -0
  145. data/plugins/project_search/vendor/lucene/examples/railway/railnet-app.rb +31 -0
  146. data/plugins/project_search/vendor/lucene/examples/railway/railnet-data.rb +42 -0
  147. data/plugins/project_search/vendor/lucene/examples/rest/example.rb +41 -0
  148. data/plugins/project_search/vendor/lucene/examples/you_might_know/YouMightKnow.java +60 -0
  149. data/plugins/project_search/vendor/lucene/examples/you_might_know/all_simple_paths.rb +34 -0
  150. data/plugins/project_search/vendor/lucene/examples/you_might_know/nodes.rb +34 -0
  151. data/plugins/project_search/vendor/lucene/examples/you_might_know/you_might_know.rb +50 -0
  152. data/plugins/project_search/vendor/lucene/lib/lucene.rb +15 -0
  153. data/plugins/project_search/vendor/lucene/lib/lucene/config.rb +145 -0
  154. data/plugins/project_search/vendor/lucene/lib/lucene/document.rb +96 -0
  155. data/plugins/project_search/vendor/lucene/lib/lucene/field_info.rb +144 -0
  156. data/plugins/project_search/vendor/lucene/lib/lucene/hits.rb +54 -0
  157. data/plugins/project_search/vendor/lucene/lib/lucene/index.rb +267 -0
  158. data/plugins/project_search/vendor/lucene/lib/lucene/index_info.rb +146 -0
  159. data/plugins/project_search/vendor/lucene/lib/lucene/index_searcher.rb +157 -0
  160. data/plugins/project_search/vendor/lucene/lib/lucene/jars.rb +5 -0
  161. data/plugins/project_search/vendor/lucene/lib/lucene/query_dsl.rb +135 -0
  162. data/plugins/project_search/vendor/lucene/lib/lucene/transaction.rb +117 -0
  163. data/plugins/project_search/vendor/lucene/lib/lucene/version.rb +3 -0
  164. data/plugins/project_search/vendor/lucene/lucene.gemspec +23 -0
  165. data/plugins/project_search/vendor/lucene/spec/lucene/document_spec.rb +32 -0
  166. data/plugins/project_search/vendor/lucene/spec/lucene/field_info_spec.rb +70 -0
  167. data/plugins/project_search/vendor/lucene/spec/lucene/index_info_spec.rb +76 -0
  168. data/plugins/project_search/vendor/lucene/spec/lucene/index_spec.rb +643 -0
  169. data/plugins/project_search/vendor/lucene/spec/lucene/query_dsl_spec.rb +142 -0
  170. data/plugins/project_search/vendor/lucene/spec/lucene/sort_spec.rb +101 -0
  171. data/plugins/project_search/vendor/lucene/spec/lucene/spec_helper.rb +10 -0
  172. data/plugins/project_search/vendor/lucene/spec/lucene/transaction_spec.rb +118 -0
  173. data/plugins/redcar/features/alter_font_size.feature +25 -0
  174. data/plugins/redcar/features/step_definitions/font_steps.rb +34 -0
  175. data/plugins/redcar/redcar.rb +256 -43
  176. data/plugins/repl/features/command_editing.feature +55 -0
  177. data/plugins/repl/features/command_history.feature +75 -0
  178. data/plugins/repl/features/step_definitions/repl_steps.rb +17 -1
  179. data/plugins/repl/features/support/env.rb +24 -0
  180. data/plugins/repl/features/support/fake_repl.rb +16 -0
  181. data/plugins/repl/lib/repl.rb +17 -74
  182. data/plugins/repl/lib/repl/repl_command.rb +20 -0
  183. data/plugins/repl/lib/repl/repl_mirror.rb +168 -22
  184. data/plugins/repl/lib/repl/repl_tab.rb +131 -6
  185. data/plugins/repl/plugin.rb +1 -1
  186. data/plugins/repl/spec/repl/repl_mirror_spec.rb +72 -0
  187. data/plugins/repl/spec/spec_helper.rb +1 -1
  188. data/plugins/repl_swt/lib/repl_swt.rb +7 -0
  189. data/plugins/repl_swt/lib/repl_swt/key_listener.rb +43 -0
  190. data/plugins/repl_swt/plugin.rb +8 -0
  191. data/plugins/ruby/lib/ruby.rb +35 -0
  192. data/plugins/{repl/lib/repl/ruby_mirror.rb → ruby/lib/ruby/repl_mirror.rb} +12 -12
  193. data/plugins/ruby/lib/{syntax_check/ruby.rb → ruby/syntax_checker.rb} +3 -3
  194. data/plugins/ruby/plugin.rb +5 -4
  195. data/plugins/{repl/spec/repl/ruby_mirror_spec.rb → ruby/spec/ruby/repl_mirror_spec.rb} +38 -29
  196. data/plugins/ruby/spec/spec_helper.rb +5 -0
  197. data/plugins/runnables/lib/runnables.rb +2 -0
  198. data/plugins/runnables/lib/runnables/command_output_controller.rb +5 -0
  199. data/plugins/runnables/lib/runnables/output_processor.rb +14 -3
  200. data/plugins/runnables/views/command_output.html.erb +3 -2
  201. data/plugins/scm/lib/scm.rb +4 -2
  202. data/plugins/scm/lib/scm/diff_mirror.rb +6 -6
  203. data/plugins/scm_git/lib/scm_git.rb +136 -107
  204. data/plugins/scm_git/lib/scm_git/change.rb +28 -19
  205. data/plugins/snippets/lib/snippets/explorer.rb +2 -2
  206. data/plugins/swt/lib/swt/full_swt.rb +1 -0
  207. data/plugins/syntax_check/features/step_definitions/syntax_check_steps.rb +4 -0
  208. data/plugins/syntax_check/features/support/env.rb +3 -0
  209. data/plugins/syntax_check/lib/syntax_check.rb +71 -5
  210. data/plugins/syntax_check/lib/syntax_check/annotation.rb +61 -0
  211. data/plugins/test_runner/lib/test_runner.rb +39 -0
  212. data/plugins/test_runner/lib/test_runner/rspec_runner.rb +20 -0
  213. data/plugins/test_runner/lib/test_runner/run_test_command.rb +63 -0
  214. data/plugins/test_runner/lib/test_runner/runnable_test_runner.rb +26 -0
  215. data/plugins/test_runner/plugin.rb +8 -0
  216. data/plugins/test_runner/spec/run_test_command_spec.rb +51 -0
  217. data/plugins/test_runner/spec/spec_helper.rb +5 -0
  218. data/plugins/textmate/lib/textmate.rb +12 -2
  219. data/plugins/textmate/vendor/redcar-bundles/Bundles/HTML.tmbundle/Syntaxes/HTML.plist +0 -2
  220. data/plugins/textmate/vendor/redcar-bundles/Bundles/Mirah.tmbundle/Syntaxes/Mirah.plist +22 -0
  221. data/plugins/textmate/vendor/redcar-bundles/Bundles/Mirah.tmbundle/info.plist +12 -0
  222. data/plugins/textmate/vendor/redcar-bundles/Bundles/Ruby.tmbundle/Syntaxes/Ruby.plist +2 -0
  223. data/plugins/todo_list/lib/todo_list.rb +7 -0
  224. data/plugins/todo_list/lib/todo_list/todo_controller.rb +3 -1
  225. data/plugins/tree/lib/tree.rb +4 -0
  226. data/plugins/tree_view_swt/lib/tree_view_swt.rb +5 -0
  227. data/plugins/web_bookmarks/lib/web_bookmarks.rb +10 -0
  228. metadata +137 -22
  229. data/plugins/document_search/features/search.feature +0 -163
  230. data/plugins/document_search/lib/document_search/replace_all_command.rb +0 -27
  231. data/plugins/document_search/lib/document_search/replace_command.rb +0 -38
  232. data/plugins/document_search/lib/document_search/replace_next_command.rb +0 -27
  233. data/plugins/document_search/lib/document_search/search_and_replace.rb +0 -81
  234. data/plugins/ruby/README +0 -6
@@ -0,0 +1,60 @@
1
+ class YouMightKnow
2
+ {
3
+ List<List<Node>> result = new ArrayList<List<Node>>();
4
+ int maxDistance;
5
+ String[] features;
6
+ Object[] values;
7
+ Set<Node> buddies = new HashSet<Node>();
8
+
9
+ YouMightKnow( Node node, String[] features, int maxDistance )
10
+ {
11
+ this.features = features;
12
+ this.maxDistance = maxDistance;
13
+ values = new Object[features.length];
14
+ List<Integer> matches = new ArrayList<Integer>();
15
+ for ( int i = 0; i < features.length; i++ )
16
+ {
17
+ values[i] = node.getProperty( features[i] );
18
+ matches.add( i );
19
+ }
20
+ for ( Relationship rel : node.getRelationships( RelationshipTypes.KNOWS ) )
21
+ {
22
+ buddies.add( rel.getOtherNode( node ) );
23
+ }
24
+ findFriends( Arrays.asList( new Node[] { node } ), matches, 1 );
25
+ }
26
+
27
+ void findFriends( List<Node> path, List<Integer> matches, int depth )
28
+ {
29
+ Node prevNode = path.get( path.size() - 1 );
30
+ for ( Relationship rel : prevNode.getRelationships( RelationshipTypes.KNOWS ) )
31
+ {
32
+ Node node = rel.getOtherNode( prevNode );
33
+ if ( (depth > 1 && buddies.contains( node )) || path.contains( node ) )
34
+ {
35
+ continue;
36
+ }
37
+ List<Integer> newMatches = new ArrayList<Integer>();
38
+ for ( int match : matches )
39
+ {
40
+ if ( node.getProperty( features[match] ).equals( values[match] ) )
41
+ {
42
+ newMatches.add( match );
43
+ }
44
+ }
45
+ if ( newMatches.size() > 0 )
46
+ {
47
+ List<Node> newPath = new ArrayList<Node>( path );
48
+ newPath.add( node );
49
+ if ( depth > 1 )
50
+ {
51
+ result.add( newPath );
52
+ }
53
+ if ( depth != maxDistance )
54
+ {
55
+ findFriends( newPath, newMatches, depth + 1 );
56
+ }
57
+ }
58
+ }
59
+ }
60
+ }
@@ -0,0 +1,34 @@
1
+ require 'rubygems'
2
+ require 'neo4j'
3
+ require 'neo4j/extensions/graph_algo'
4
+ include Neo4j
5
+
6
+ # In this case we want to know the possible paths from one person in a social network to an other.
7
+ # With those paths at hand we can do things similar to the "How you're connected to N.N." feature of LinkedIn.
8
+
9
+
10
+
11
+ Transaction.new
12
+
13
+ load "nodes.rb"
14
+
15
+ node1,node2,node3,node4,node5,node6,node7 = create_nodes
16
+
17
+ found_nodes = GraphAlgo.all_simple_paths.from(node1).both(:knows).to(node7).depth(4).as_nodes
18
+ puts "Nodes between #{node1} and #{node7}"
19
+ found_nodes.each do |path|
20
+ puts "path"
21
+ path.each {|node| puts " #{node}" }
22
+ end
23
+
24
+ sorted = found_nodes.sort_by{|path| 10 - path.size}
25
+
26
+ puts "sorted: "
27
+ sorted.each do |path|
28
+ puts "path"
29
+ path.each {|node| puts " #{node}" }
30
+ end
31
+
32
+ Transaction.finish
33
+
34
+ Neo4j.stop
@@ -0,0 +1,34 @@
1
+ # -----------------------------------------------------------------------------
2
+
3
+ # Add a to string method printing the node name
4
+ class Node
5
+ include Neo4j::NodeMixin
6
+
7
+ def to_s
8
+ "Node #{self[:name]}"
9
+ end
10
+ end
11
+
12
+ def create_nodes
13
+ node1 = Node.new; node1[:feat1] = 'a'; node1[:feat2] = 'b'; node1[:name] = 1
14
+ node2 = Node.new; node2[:feat1] = 'a'; node2[:feat2] = 'b'; node2[:name] = 2
15
+ node3 = Node.new; node3[:feat1] = 'a'; node3[:feat2] = 'd'; node3[:name] = 3
16
+ node4 = Node.new; node4[:feat1] = 'c'; node4[:feat2] = 'd'; node4[:name] = 4
17
+ node5 = Node.new; node5[:feat1] = 'a'; node5[:feat2] = 'b'; node5[:name] = 5
18
+ node6 = Node.new; node6[:feat1] = 'a'; node6[:feat2] = 'b'; node6[:name] = 6
19
+ node7 = Node.new; node7[:feat1] = 'a'; node7[:feat2] = 'b'; node7[:name] = 7
20
+
21
+ node1.rels.outgoing(:knows) << node3
22
+ node2.rels.outgoing(:knows) << node1
23
+ node2.rels.outgoing(:knows) << node4
24
+ node3.rels.outgoing(:knows) << node5
25
+ node3.rels.outgoing(:knows) << node4
26
+ node3.rels.outgoing(:knows) << node6
27
+ node4.rels.outgoing(:knows) << node7
28
+ node5.rels.outgoing(:knows) << node6
29
+ node5.rels.outgoing(:knows) << node1
30
+ node6.rels.outgoing(:knows) << node1
31
+
32
+ [node1,node2,node3,node4,node5,node6,node7]
33
+ end
34
+
@@ -0,0 +1,50 @@
1
+ require 'rubygems'
2
+ require 'neo4j'
3
+ include Neo4j
4
+
5
+
6
+ # The challenge this time is to traverse into friends of friends (or even deeper) and find people with something in common.
7
+ # Based on this we can distill someone the user might know, or could be interested in knowing.
8
+ # The persons in our social network all have different values for two features, feat1 and feat2.
9
+ # The idea of the solution presented here is to keep track of the features that are common in each branch of the traversal
10
+ # and to stop when there is nothing in common any more or the maximum distance has been reached.
11
+ def you_might_know(node, matches, max_distance)
12
+ buddies = [*node.rels.both(:knows).nodes]
13
+ find_friends(node, [node], matches, 1, max_distance, buddies)
14
+ end
15
+
16
+ def find_friends(root_node, path, matches, depth, max_distance, buddies)
17
+ result = []
18
+ path.last.rels.both(:knows).nodes.each do |node|
19
+ next if (depth > 1 && buddies.include?(node)) || path.include?(node)
20
+ new_matches = matches.find_all{|feature| root_node[feature] == node[feature]}
21
+ next if new_matches.empty?
22
+ new_path = path + [node]
23
+ result = [new_path] + result if depth > 1
24
+ result += find_friends(node, new_path, new_matches, depth + 1, max_distance, buddies) if depth != max_distance
25
+ end
26
+ result
27
+ end
28
+
29
+
30
+ puts "-----------------------"
31
+ puts "YOU MIGHT KNOW"
32
+ puts "-----------------------"
33
+
34
+
35
+ Transaction.new
36
+
37
+ load "nodes.rb"
38
+
39
+ node1,node2,node3,node4,node5,node6,node7 = create_nodes
40
+
41
+ result = you_might_know(node5, [:feat1, :feat2], 4)
42
+ result.each do |list|
43
+ puts "You might know nodes"
44
+ list.each {|n| puts n}
45
+ end
46
+
47
+ Transaction.finish
48
+ Neo4j.stop
49
+
50
+
@@ -0,0 +1,15 @@
1
+ require 'logger'
2
+ $LUCENE_LOGGER = Logger.new(STDOUT)
3
+ $LUCENE_LOGGER.level = Logger::WARN
4
+
5
+ require 'lucene/config'
6
+ require 'lucene/document'
7
+ require 'lucene/field_info'
8
+ require 'lucene/hits'
9
+ require 'lucene/index'
10
+ require 'lucene/index_info'
11
+ require 'lucene/index_searcher'
12
+ require 'lucene/jars'
13
+ require 'lucene/query_dsl'
14
+ require 'lucene/transaction'
15
+
@@ -0,0 +1,145 @@
1
+
2
+ module Lucene
3
+
4
+
5
+ #
6
+ # Keeps configuration for lucene.
7
+ # Contains both common configuration for all lucene indexes as well
8
+ # as specific configuration for each index (TODO).
9
+ # This code is copied from merb-core/config.rb.
10
+ #
11
+ # Contains three default configurations (Config.defaults)
12
+ # * :store_on_file:: default false, which will only keep the index in memory
13
+ # * :id_field:: default :id
14
+ # * :storage_path:: where the index is kept on file system if stored as a file (instead of just in memory)
15
+ #
16
+ class Config
17
+ class << self
18
+ # Returns the hash of default config values for lucene.
19
+ #
20
+ # ==== Returns
21
+ # Hash:: The defaults for the config.
22
+ #
23
+ def defaults
24
+ @defaults ||= {
25
+ :store_on_file => false,
26
+ :id_field => :id,
27
+ :storage_path => nil
28
+ }
29
+ end
30
+
31
+
32
+ # Yields the configuration.
33
+ #
34
+ # ==== Block parameters
35
+ # c<Hash>:: The configuration parameters.
36
+ #
37
+ # ==== Examples
38
+ # Lucene::Config.use do |config|
39
+ # config[:in_memory] = true
40
+ # end
41
+ #
42
+ # ==== Returns
43
+ # nil
44
+ #
45
+ def use
46
+ @configuration ||= {}
47
+ yield @configuration
48
+ nil
49
+ end
50
+
51
+
52
+ # Set the value of a config entry.
53
+ #
54
+ # ==== Parameters
55
+ # key<Object>:: The key to set the parameter for.
56
+ # val<Object>:: The value of the parameter.
57
+ #
58
+ def []=(key, val)
59
+ (@configuration ||= setup)[key] = val
60
+ end
61
+
62
+
63
+ # Gets the the value of a config entry
64
+ #
65
+ # ==== Parameters
66
+ # key<Object>:: The key of the config entry value we want
67
+ #
68
+ def [](key)
69
+ (@configuration ||= setup)[key]
70
+ end
71
+
72
+
73
+ # Remove the value of a config entry.
74
+ #
75
+ # ==== Parameters
76
+ # key<Object>:: The key of the parameter to delete.
77
+ #
78
+ # ==== Returns
79
+ # Object:: The value of the removed entry.
80
+ #
81
+ def delete(key)
82
+ @configuration.delete(key)
83
+ end
84
+
85
+
86
+ # Remove all configuration. This can be useful for testing purpose.
87
+ #
88
+ #
89
+ # ==== Returns
90
+ # nil
91
+ #
92
+ def delete_all
93
+ @configuration = nil
94
+ IndexInfo.delete_all
95
+ end
96
+
97
+
98
+ # Retrieve the value of a config entry, returning the provided default if the key is not present
99
+ #
100
+ # ==== Parameters
101
+ # key<Object>:: The key to retrieve the parameter for.
102
+ # default<Object>::
103
+ # The default value to return if the parameter is not set.
104
+ #
105
+ # ==== Returns
106
+ # Object:: The value of the configuration parameter or the default.
107
+ #
108
+ def fetch(key, default)
109
+ @configuration.fetch(key, default)
110
+ end
111
+
112
+ # Sets up the configuration
113
+ #
114
+ # ==== Returns
115
+ # The configuration as a hash.
116
+ #
117
+ def setup()
118
+ @configuration = {}
119
+ @configuration.merge!(defaults)
120
+ @configuration
121
+ end
122
+
123
+
124
+ # Returns the configuration as a hash.
125
+ #
126
+ # ==== Returns
127
+ # Hash:: The config as a hash.
128
+ #
129
+ def to_hash
130
+ @configuration
131
+ end
132
+
133
+ # Returns the config as YAML.
134
+ #
135
+ # ==== Returns
136
+ # String:: The config as YAML.
137
+ #
138
+ def to_yaml
139
+ require "yaml"
140
+ @configuration.to_yaml
141
+ end
142
+ end
143
+ end
144
+
145
+ end
@@ -0,0 +1,96 @@
1
+ module Lucene
2
+
3
+ #
4
+ # A document is like a record or row in a relationship database.
5
+ # Contains the field infos which can be used for type conversions or
6
+ # specifying if the field should be stored or only searchable.
7
+ #
8
+ class Document
9
+
10
+ attr_reader :id_field, :field_infos, :props
11
+
12
+ def initialize(field_infos, props = {})
13
+ @id_field = field_infos.id_field
14
+ @field_infos = field_infos
15
+
16
+ @props = {}
17
+ props.each_pair do |key,value|
18
+ @props[key] = field_infos[key].convert_to_ruby(value)
19
+ $LUCENE_LOGGER.debug{"FieldInfo #{key} type: #{field_infos[key][:type]}"}
20
+ $LUCENE_LOGGER.debug{"Converted #{key} '#{value}' type: '#{value.class.to_s}' to '#{@props[key]}' type: '#{@props[key].class.to_s}'"}
21
+ end
22
+ end
23
+
24
+ def [](key)
25
+ @props[key]
26
+ end
27
+
28
+ #
29
+ # Convert a java Document to a ruby Lucene::Document
30
+ #
31
+ def self.convert(field_infos, java_doc)
32
+ fields = {}
33
+ field_infos.each_pair do |key, field|
34
+ next unless field.store?
35
+ raise StandardError.new("expected field '#{key.to_s}' to exist in document") if java_doc.getField(key.to_s).nil?
36
+ value = java_doc.getField(key.to_s).stringValue
37
+ fields.merge!({key => value})
38
+ end
39
+ Document.new(field_infos, fields)
40
+ end
41
+
42
+ def id
43
+ raise IdFieldMissingException.new("Missing id field: '#{@id_field}'") if self[@id_field].nil?
44
+ @props[@id_field]
45
+ end
46
+
47
+ def eql?(other)
48
+ return false unless other.is_a? Document
49
+ return id == other.id
50
+ end
51
+
52
+ def ==(other)
53
+ eql?(other)
54
+ end
55
+
56
+ def hash
57
+ id.hash
58
+ end
59
+
60
+ #
61
+ # removes the document and adds it again
62
+ #
63
+ def update(index_writer)
64
+ index_writer.updateDocument(java_key_term, java_document)
65
+ end
66
+
67
+
68
+ def java_key_term
69
+ org.apache.lucene.index.Term.new(@id_field.to_s, id.to_s)
70
+ end
71
+
72
+ def java_document
73
+ java_doc = org.apache.lucene.document.Document.new
74
+ @props.each_pair do |key,value|
75
+ field_info = @field_infos[key]
76
+ # TODO value could be an array if value.kind_of? Enumerable
77
+ if (value.kind_of?(Array))
78
+ value.each do |v|
79
+ field = field_info.java_field(key,v)
80
+ java_doc.add(field) unless field.nil?
81
+ end
82
+ else
83
+ field = field_info.java_field(key,value)
84
+ java_doc.add(field) unless field.nil?
85
+ end
86
+ end
87
+ java_doc
88
+ end
89
+
90
+ def to_s
91
+ p = ""
92
+ @props.each_pair { |key,value| p << "'#{key}' = '#{value}' " }
93
+ "Document [#@id_field='#{self[@id_field]}', #{p}]"
94
+ end
95
+ end
96
+ end
@@ -0,0 +1,144 @@
1
+ require 'date'
2
+
3
+ module Lucene
4
+ class ConversionNotSupportedException < StandardError; end
5
+
6
+ class FieldInfo
7
+ DEFAULTS = {:store => false, :type => String, :analyzer => :standard}.freeze
8
+
9
+ def initialize(values = {})
10
+ @info = DEFAULTS.dup
11
+ @info.merge! values
12
+ $LUCENE_LOGGER.debug{"new FieldInfo: #{@info.inspect}"}
13
+ end
14
+
15
+ def dup
16
+ FieldInfo.new(@info)
17
+ end
18
+
19
+ def [](key)
20
+ @info[key]
21
+ end
22
+
23
+ def []=(key,value)
24
+ @info[key] = value
25
+ end
26
+
27
+ def java_field(key, value)
28
+ # convert the ruby value to a string that lucene can handle
29
+ cvalue = convert_to_lucene(value)
30
+
31
+ # check if this field should be indexed
32
+ return nil if cvalue.nil?
33
+
34
+ # decide if the field should be stored in the lucene index or not
35
+ store = store? ? org.apache.lucene.document.Field::Store::YES : org.apache.lucene.document.Field::Store::NO
36
+
37
+ # decide if it should be tokenized/analyzed by lucene
38
+ token_type = tokenized? ? org.apache.lucene.document.Field::Index::ANALYZED : org.apache.lucene.document.Field::Index::NOT_ANALYZED
39
+ $LUCENE_LOGGER.debug{"java_field store=#{store} key='#{key.to_s}' value='#{cvalue}' token_type=#{token_type}"}
40
+
41
+ # create the new Field
42
+ org.apache.lucene.document.Field.new(key.to_s, cvalue, store, token_type ) #org.apache.lucene.document.Field::Index::NO_NORMS)
43
+ end
44
+
45
+
46
+ def convert_to_ruby(value)
47
+ if (value.kind_of?(Array))
48
+ value.collect{|v| convert_to_ruby(v)}
49
+ else case @info[:type].to_s
50
+ when NilClass.to_s then "" # TODO, should we accept nil values in indexes ?
51
+ when String.to_s then value.to_s
52
+ when Fixnum.to_s then value.to_i
53
+ when Float.to_s then value.to_f
54
+ when Date.to_s
55
+ return value if value.kind_of? Date
56
+ return nil if value.nil?
57
+ year = value[0..3].to_i
58
+ month = value[4..5].to_i
59
+ day = value[6..7].to_i
60
+ Date.new year,month,day
61
+ when DateTime.to_s
62
+ return value if value.kind_of? DateTime
63
+ return nil if value.nil?
64
+ year = value[0..3].to_i
65
+ month = value[4..5].to_i
66
+ day = value[6..7].to_i
67
+ hour = value[8..9].to_i
68
+ min = value[10..11].to_i
69
+ sec = value[12..13].to_i
70
+ DateTime.civil(year,month,day,hour,min,sec)
71
+ else
72
+ raise ConversionNotSupportedException.new("Can't convert key '#{value}' of with type '#{@info[:type].class.to_s}'")
73
+ end
74
+ end
75
+ end
76
+
77
+ def convert_to_lucene(value)
78
+ if (value.kind_of?(Array))
79
+ value.collect{|v| convert_to_lucene(v)}
80
+ elsif value.nil?
81
+ value
82
+ else
83
+ case @info[:type].to_s # otherwise it will match Class
84
+ when Fixnum.to_s then sprintf('%011d',value) # TODO: configurable
85
+ when Float.to_s then sprintf('%024.12f', value) # TODO: configurable
86
+ when Bignum.to_s then sprintf('%024d, value')
87
+ when Date.to_s
88
+ t = Time.utc(value.year, value.month, value.day)
89
+ d = t.to_i * 1000
90
+ org.apache.lucene.document.DateTools.timeToString(d,org.apache.lucene.document.DateTools::Resolution::DAY )
91
+ when DateTime.to_s
92
+ # only utc times are supported
93
+ t = Time.utc(value.year, value.month, value.day, value.hour, value.min, value.sec)
94
+ d = t.to_i * 1000
95
+ org.apache.lucene.document.DateTools.timeToString(d,org.apache.lucene.document.DateTools::Resolution::SECOND )
96
+ else value.to_s
97
+ end
98
+ end
99
+ end
100
+
101
+ def convert_to_query(key,value)
102
+ if (value.kind_of? Range)
103
+ first_value = convert_to_lucene(value.first)
104
+ last_value = convert_to_lucene(value.last)
105
+ first = org.apache.lucene.index.Term.new(key.to_s, first_value)
106
+ last = org.apache.lucene.index.Term.new(key.to_s, last_value)
107
+ $LUCENE_LOGGER.debug{"convert_to_query: Range key '#{key.to_s}' #{first_value}' to '#{last_value}'"}
108
+ org.apache.lucene.search.RangeQuery.new(first, last, !value.exclude_end?)
109
+ elsif
110
+ converted_value = convert_to_lucene(value)
111
+ term = org.apache.lucene.index.Term.new(key.to_s, converted_value)
112
+ org.apache.lucene.search.TermQuery.new(term)
113
+ end
114
+ end
115
+
116
+ def tokenized?
117
+ @info[:tokenized]
118
+ end
119
+
120
+ def store?
121
+ @info[:store]
122
+ end
123
+
124
+ def eql?(other)
125
+ return false unless other.kind_of?(FieldInfo)
126
+ @info.each_pair do |key,value|
127
+ return false if other[key] != value
128
+ end
129
+ return true
130
+ end
131
+
132
+ def ==(other)
133
+ eql? other
134
+ end
135
+
136
+ def to_s
137
+ infos = @info.keys.inject(""){|s, key| s << "#{key}=#{@info[key]} "}
138
+ "FieldInfo(#{self.object_id.to_s}) [#{infos}]"
139
+ end
140
+
141
+
142
+ end
143
+ end
144
+