n4j 0.0.1
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.
- data/.gitignore +6 -0
- data/.rvmrc +2 -0
- data/Gemfile +6 -0
- data/README.rdoc +5 -0
- data/Rakefile +137 -0
- data/config/n4j.yml +7 -0
- data/lib/n4j.rb +46 -0
- data/lib/n4j/attributes.rb +48 -0
- data/lib/n4j/auto_relate.rb +41 -0
- data/lib/n4j/cypher.rb +45 -0
- data/lib/n4j/entity.rb +117 -0
- data/lib/n4j/field.rb +26 -0
- data/lib/n4j/node.rb +91 -0
- data/lib/n4j/populate.rb +22 -0
- data/lib/n4j/relationship.rb +47 -0
- data/lib/n4j/representation.rb +63 -0
- data/lib/n4j/request.rb +39 -0
- data/lib/n4j/traversal.rb +62 -0
- data/lib/n4j/version.rb +3 -0
- data/n4j.gemspec +26 -0
- data/neo4j_plugins/test-delete-db-extension-1.5.jar +0 -0
- data/tasks/.gitkeep +0 -0
- data/tasks/n4j.rake +125 -0
- data/templates/README.txt +16 -0
- data/templates/logging.properties +73 -0
- data/templates/neo4j-server-1.5.properties +53 -0
- data/templates/neo4j-server-1.6.properties +78 -0
- data/templates/neo4j-wrapper.conf +37 -0
- data/templates/neo4j.properties +9 -0
- data/templates/windows-wrapper-logging.properties +73 -0
- data/test/basics_test.rb +46 -0
- data/test/field_test.rb +19 -0
- data/test/test_helper.rb +12 -0
- metadata +121 -0
data/lib/n4j/field.rb
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
module N4j::Field
|
2
|
+
extend ActiveSupport::Concern
|
3
|
+
included do
|
4
|
+
end
|
5
|
+
module ClassMethods
|
6
|
+
def field(name)
|
7
|
+
define_method name do
|
8
|
+
data_access(name.to_s)
|
9
|
+
end
|
10
|
+
|
11
|
+
define_method "#{name}=" do |value|
|
12
|
+
data_set(name, value)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def data_access(key)
|
18
|
+
data[key]
|
19
|
+
end
|
20
|
+
|
21
|
+
def data_set(key, new_value)
|
22
|
+
new_data = data.merge({key.to_s => new_value})
|
23
|
+
self.data = new_data
|
24
|
+
end
|
25
|
+
|
26
|
+
end
|
data/lib/n4j/node.rb
ADDED
@@ -0,0 +1,91 @@
|
|
1
|
+
module N4j::Node
|
2
|
+
|
3
|
+
autoload :AutoRelate, 'n4j/auto_relate'
|
4
|
+
|
5
|
+
extend ActiveSupport::Concern
|
6
|
+
included do
|
7
|
+
include AutoRelate
|
8
|
+
# include N4j::Entity
|
9
|
+
end
|
10
|
+
module ClassMethods
|
11
|
+
def find(n)
|
12
|
+
find_by_node_id(n)
|
13
|
+
end
|
14
|
+
|
15
|
+
def find_by_node_id(n)
|
16
|
+
find_by_path("/node/#{n}")
|
17
|
+
end
|
18
|
+
|
19
|
+
def find_by_path(path)
|
20
|
+
path.sub!(N4j.neo4j_url_prefix,'')
|
21
|
+
result = N4j.batch([{:to => path, :method => 'GET'}])
|
22
|
+
new(result.first['body'])
|
23
|
+
end
|
24
|
+
|
25
|
+
def service_root
|
26
|
+
find_by_node_id(0)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def initialize(hsh)
|
31
|
+
super(hsh)
|
32
|
+
unless N4j.neo4j_hash?(hsh)
|
33
|
+
self.data = hsh.dup
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def create_path
|
38
|
+
'/node'
|
39
|
+
end
|
40
|
+
|
41
|
+
def body_hash
|
42
|
+
data
|
43
|
+
end
|
44
|
+
|
45
|
+
def dependent
|
46
|
+
relationships
|
47
|
+
end
|
48
|
+
|
49
|
+
def connected_unsaved
|
50
|
+
new_relationships
|
51
|
+
end
|
52
|
+
|
53
|
+
def post_save
|
54
|
+
clear_new_relationships!
|
55
|
+
end
|
56
|
+
|
57
|
+
def relationships(direction = 'all_relationships', types = [], clear_cache = false)
|
58
|
+
@relationship_cache ||= {}
|
59
|
+
if persisted?
|
60
|
+
path = from_neo4j_relative[direction] + '/' + [types].flatten.join('&')
|
61
|
+
@relationship_cache.delete(path) if clear_cache
|
62
|
+
@relationship_cache[path] ||= GenericRelationship.find_by_node_path(path)
|
63
|
+
else
|
64
|
+
[]
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
def entity_type
|
69
|
+
'node'
|
70
|
+
end
|
71
|
+
|
72
|
+
def traverse(opts = {})
|
73
|
+
# Started this approach, stoppedto investigate Cypher
|
74
|
+
defaults = {:start => path, :instantiate_with => self.class }
|
75
|
+
N4j::Traversal.new(:start => path)
|
76
|
+
end
|
77
|
+
|
78
|
+
def cypher(opts = {})
|
79
|
+
defaults = {:start => self}
|
80
|
+
N4j::Cypher.new(defaults.merge(opts))
|
81
|
+
end
|
82
|
+
|
83
|
+
def new_relationships
|
84
|
+
@new_relationships ||= []
|
85
|
+
end
|
86
|
+
|
87
|
+
def clear_new_relationships!
|
88
|
+
@new_relationships = []
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
data/lib/n4j/populate.rb
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
module N4j::Relationship::Populate
|
2
|
+
extend ActiveSupport::Concern
|
3
|
+
included do
|
4
|
+
end
|
5
|
+
module ClassMethods
|
6
|
+
end
|
7
|
+
|
8
|
+
def start
|
9
|
+
if super.kind_of?(String)
|
10
|
+
@start = GenericNode.find_by_path(super)
|
11
|
+
else
|
12
|
+
super
|
13
|
+
end
|
14
|
+
end
|
15
|
+
def end
|
16
|
+
if super.kind_of?(String)
|
17
|
+
@end = GenericNode.find_by_path(super)
|
18
|
+
else
|
19
|
+
super
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
module N4j::Relationship
|
2
|
+
autoload :Populate, 'n4j/populate'
|
3
|
+
extend ActiveSupport::Concern
|
4
|
+
included do
|
5
|
+
attr_writer :type
|
6
|
+
|
7
|
+
attribute :start
|
8
|
+
attribute :end
|
9
|
+
include Populate
|
10
|
+
end
|
11
|
+
|
12
|
+
module ClassMethods
|
13
|
+
end
|
14
|
+
|
15
|
+
def initialize(hsh)
|
16
|
+
if N4j.neo4j_hash?(hsh)
|
17
|
+
super(hsh)
|
18
|
+
else
|
19
|
+
opts = HashWithIndifferentAccess.new.merge(hsh)
|
20
|
+
opts.each_pair do |k,v|
|
21
|
+
send("#{k}=",v) if %w(start end data type).include?(k)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def entity_type
|
27
|
+
'relationship'
|
28
|
+
end
|
29
|
+
|
30
|
+
def prerequisites
|
31
|
+
[self.start, self.end]
|
32
|
+
end
|
33
|
+
|
34
|
+
def create_path
|
35
|
+
start.from_neo4j_relative['create_relationship'] ||
|
36
|
+
"#{start.path}/relationships"
|
37
|
+
end
|
38
|
+
|
39
|
+
def body_hash
|
40
|
+
{:to => self.end.path, :data => data, :type => type}
|
41
|
+
end
|
42
|
+
|
43
|
+
def type
|
44
|
+
@type ||= self.class.model_name.i18n_key
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
@@ -0,0 +1,63 @@
|
|
1
|
+
module N4j::Entity::Representation
|
2
|
+
extend ActiveSupport::Concern
|
3
|
+
included do
|
4
|
+
include Comparable
|
5
|
+
end
|
6
|
+
module ClassMethods
|
7
|
+
end
|
8
|
+
|
9
|
+
def <=>(another_object)
|
10
|
+
if self.class.ancestors.include?(N4j::Entity)
|
11
|
+
url <=> another_object.url
|
12
|
+
else
|
13
|
+
super(another_object)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def to_key
|
18
|
+
persisted? ? [path[/\d+\Z/]] : nil
|
19
|
+
end
|
20
|
+
|
21
|
+
def url
|
22
|
+
from_neo4j['self']
|
23
|
+
end
|
24
|
+
|
25
|
+
def path
|
26
|
+
from_neo4j_relative['self'] ||
|
27
|
+
(place_in_batch ? "{#{place_in_batch}}" : nil)
|
28
|
+
end
|
29
|
+
|
30
|
+
def create_path
|
31
|
+
raise 'Override in Node/Relationship'
|
32
|
+
end
|
33
|
+
|
34
|
+
def update_path
|
35
|
+
from_neo4j_relative['properties']
|
36
|
+
end
|
37
|
+
|
38
|
+
def body_hash
|
39
|
+
raise 'Override in Node/Relationship'
|
40
|
+
end
|
41
|
+
|
42
|
+
def persist_hash(opts = {})
|
43
|
+
if needs_persist?
|
44
|
+
persisted? ? update_hash(opts) : create_hash(opts)
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
def create_hash(opts={})
|
49
|
+
{ :to => create_path, :method => 'POST', :body => body_hash }.merge(opts)
|
50
|
+
end
|
51
|
+
|
52
|
+
def update_hash(opts={})
|
53
|
+
{:to => update_path, :method => 'PUT', :body => body_hash}.merge(opts)
|
54
|
+
end
|
55
|
+
|
56
|
+
def destroy_hash(opts={})
|
57
|
+
{:to => path, :method => 'DELETE'}.merge(opts)
|
58
|
+
end
|
59
|
+
|
60
|
+
def show_hash(opts={})
|
61
|
+
{:to => path, :method => 'GET'}.merge(opts)
|
62
|
+
end
|
63
|
+
end
|
data/lib/n4j/request.rb
ADDED
@@ -0,0 +1,39 @@
|
|
1
|
+
module N4j::Request
|
2
|
+
extend ActiveSupport::Concern
|
3
|
+
included do
|
4
|
+
end
|
5
|
+
module ClassMethods
|
6
|
+
def neo4j_url_prefix
|
7
|
+
@neo4j_url_prefix ||= "http://localhost:#{port}/db/data"
|
8
|
+
end
|
9
|
+
|
10
|
+
def port
|
11
|
+
config = YAML.load_file("#{Rails.root}/config/n4j.yml")
|
12
|
+
config[Rails.env]['port']
|
13
|
+
end
|
14
|
+
|
15
|
+
def neo4j_hash?(hsh)
|
16
|
+
hsh && hsh['self'] && hsh['property'] && hsh['properties']
|
17
|
+
end
|
18
|
+
|
19
|
+
def batch(commands) # [{'to'=> '', 'method' => '', 'body' => '', 'id' => 0},...]
|
20
|
+
commands.flatten!
|
21
|
+
commands.each_with_index {|command, index| command[:id] ||= index }
|
22
|
+
# puts "Batch job: #{commands.inspect}"
|
23
|
+
begin
|
24
|
+
result = RestClient.post("#{neo4j_url_prefix}/batch",
|
25
|
+
commands.to_json,
|
26
|
+
:accept => :json,
|
27
|
+
:content_type => :json)
|
28
|
+
JSON.parse(result)
|
29
|
+
rescue RestClient::InternalServerError => e
|
30
|
+
message = JSON.parse(JSON.parse(e.response)['message'])['message']
|
31
|
+
exception = JSON.parse(JSON.parse(e.response)['message'])['exception']
|
32
|
+
puts "Neo4j error: #{message}" if message
|
33
|
+
puts "Neo4j excpetion: #{exception}" if exception
|
34
|
+
rescue JSON::ParserError => e
|
35
|
+
puts "JSON::ParserError ... raw result:\n #{result}"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
class N4j::Traversal
|
2
|
+
PARAMETERS = [:order, :uniqueness, :return_filter, :prune_evaluator, :relationships, :max_depth]
|
3
|
+
attr_accessor *PARAMETERS
|
4
|
+
attr_accessor :start, :return_type
|
5
|
+
|
6
|
+
def initialize(opts ={})
|
7
|
+
opts.each_pair do |k,v|
|
8
|
+
send "#{k}=", v if respond_to?("#{k}=")
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
def return_type
|
13
|
+
@return_type || 'node'
|
14
|
+
end
|
15
|
+
|
16
|
+
def outbound(type)
|
17
|
+
self.relationships ||= []
|
18
|
+
self.relationships << {'direction' => 'out', 'type' => type}
|
19
|
+
self
|
20
|
+
end
|
21
|
+
|
22
|
+
def inbound(type)
|
23
|
+
self.relationships ||= []
|
24
|
+
self.relationships << {'direction' => 'in', 'type' => type}
|
25
|
+
self
|
26
|
+
end
|
27
|
+
|
28
|
+
# {
|
29
|
+
# "order" : "breadth_first",
|
30
|
+
# "return_filter" : {
|
31
|
+
# "body" : "position.endNode().getProperty('name').toLowerCase().contains('t')",
|
32
|
+
# "language" : "javascript"
|
33
|
+
# },
|
34
|
+
# "prune_evaluator" : {
|
35
|
+
# "body" : "position.length() > 10",
|
36
|
+
# "language" : "javascript"
|
37
|
+
# },
|
38
|
+
# "uniqueness" : "node_global",
|
39
|
+
# "relationships" : [ {
|
40
|
+
# "direction" : "all",
|
41
|
+
# "type" : "knows"
|
42
|
+
# }, {
|
43
|
+
# "direction" : "all",
|
44
|
+
# "type" : "loves"
|
45
|
+
# } ],
|
46
|
+
# "max_depth" : 3
|
47
|
+
# }
|
48
|
+
|
49
|
+
def traversal
|
50
|
+
# {"relationships" => [{'direction' => 'in', 'type' => 'is_a' }]}
|
51
|
+
self.class::PARAMETERS.inject({}) do |sum, n|
|
52
|
+
key = :"@#{n}"
|
53
|
+
val = instance_variable_defined?(key) && instance_variable_get(key)
|
54
|
+
sum[n] = val if val
|
55
|
+
sum
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
def go
|
60
|
+
N4j.batch([{:to => "#{start}/traverse/#{return_type}", :method => 'POST', :body => traversal}])
|
61
|
+
end
|
62
|
+
end
|
data/lib/n4j/version.rb
ADDED
data/n4j.gemspec
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
require "n4j/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "n4j"
|
7
|
+
s.version = N4j::VERSION
|
8
|
+
s.authors = ["Sam Schenkman-Moore"]
|
9
|
+
s.email = ["samsm@samsm.com"]
|
10
|
+
s.homepage = ""
|
11
|
+
s.summary = %q{Help using Neo4j Rest server.}
|
12
|
+
s.description = %q{A little spiked out thing.}
|
13
|
+
|
14
|
+
s.rubyforge_project = "n4j"
|
15
|
+
|
16
|
+
s.files = `git ls-files`.split("\n")
|
17
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
18
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
19
|
+
s.require_paths = ["lib"]
|
20
|
+
|
21
|
+
# specify any dependencies here; for example:
|
22
|
+
# s.add_development_dependency "rspec"
|
23
|
+
s.add_runtime_dependency "rest-client"
|
24
|
+
s.add_runtime_dependency "activesupport"
|
25
|
+
s.add_runtime_dependency "activemodel"
|
26
|
+
end
|
Binary file
|
data/tasks/.gitkeep
ADDED
File without changes
|
data/tasks/n4j.rake
ADDED
@@ -0,0 +1,125 @@
|
|
1
|
+
require 'erb'
|
2
|
+
|
3
|
+
namespace :n4j do
|
4
|
+
|
5
|
+
desc "Bug du jour"
|
6
|
+
task :bug => :environment do
|
7
|
+
require 'n4j'
|
8
|
+
gn = GenericNode.new({:test => 'foo'})
|
9
|
+
gn.save
|
10
|
+
gn.data = {:test => 'bar'}
|
11
|
+
gn.save
|
12
|
+
end
|
13
|
+
|
14
|
+
desc "Clear development database."
|
15
|
+
task :clear_development do
|
16
|
+
port = YAML.parse_file('config/n4j.yml').to_ruby['development']['port']
|
17
|
+
result = `curl --request DELETE http://localhost:#{port}/cleandb/all-gone`
|
18
|
+
puts result
|
19
|
+
end
|
20
|
+
|
21
|
+
desc "Status of Neo4j servers"
|
22
|
+
task :status do
|
23
|
+
number_of_neo4j_instances = `ps aux | grep ne[o]4j | wc -l`
|
24
|
+
number_of_neo4j_instances.strip!
|
25
|
+
puts "#{number_of_neo4j_instances} total instances of Neo4j running, system wide."
|
26
|
+
unless number_of_neo4j_instances.to_i < 1
|
27
|
+
YAML.parse_file('config/n4j.yml').to_ruby.each_pair do |environment, conf|
|
28
|
+
pid = IO.read "tmp/pids/n4j_#{environment}_pid"
|
29
|
+
pid.chomp!
|
30
|
+
result = `ps p#{pid} | grep #{pid} | wc -l`
|
31
|
+
result.strip!
|
32
|
+
puts "#{result} instances running for #{environment} (pid: #{pid})."
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
desc 'Start servers'
|
38
|
+
task :start do |task_name|
|
39
|
+
YAML.parse_file('config/n4j.yml').to_ruby.each_pair do |environment, conf|
|
40
|
+
@environment = environment
|
41
|
+
@port = conf['port']
|
42
|
+
@secure_port = conf['secure_port']
|
43
|
+
@server_version = 1.6
|
44
|
+
|
45
|
+
neo4j_bin_link = `which neo4j`
|
46
|
+
neo4j_bin_link.chomp!
|
47
|
+
neo4j_bin = Pathname.new(neo4j_bin_link).realpath
|
48
|
+
|
49
|
+
libexec = Pathname.new(neo4j_bin_link).realpath.dirname.dirname
|
50
|
+
|
51
|
+
libdir = "#{libexec}/lib"
|
52
|
+
syslib = "#{libexec}/system/lib"
|
53
|
+
plugin_dir = "#{libexec}/plugins"
|
54
|
+
n4j_plugins = 'lib/n4j/neo4j_plugins'
|
55
|
+
# coordinator ???
|
56
|
+
|
57
|
+
class_path = [libdir, syslib, plugin_dir, n4j_plugins].collect {|dir| Dir.glob(dir + '/*.jar')}.flatten.join(':')
|
58
|
+
|
59
|
+
java_opts = "-server -XX:+DisableExplicitGC -Dorg.neo4j.server.properties=conf/neo4j-server.properties -Djava.util.logging.config.file=conf/logging.properties -Xms3m -Xmx64m"
|
60
|
+
|
61
|
+
|
62
|
+
|
63
|
+
neo4j_home = "tmp/n4j/#{@environment}"
|
64
|
+
|
65
|
+
FileUtils.mkdir_p neo4j_home
|
66
|
+
FileUtils.mkdir_p "#{neo4j_home}/data/log"
|
67
|
+
|
68
|
+
FileUtils.mkdir_p 'tmp/pids'
|
69
|
+
pid_file = "tmp/pids/n4j_#{@environment}_pid"
|
70
|
+
|
71
|
+
java_command = `which java`
|
72
|
+
java_command.chomp!
|
73
|
+
|
74
|
+
system "cp lib/n4j/templates/neo4j.properties tmp/n4j/#{@environment}/"
|
75
|
+
system "cp lib/n4j/templates/logging.properties tmp/n4j/#{@environment}/"
|
76
|
+
|
77
|
+
system " touch #{neo4j_home}/data/log/console.log"
|
78
|
+
|
79
|
+
neo4j_server_properties = "##### Genereated file! May be overwritten. ##### \n" +
|
80
|
+
ERB.new(IO.read("lib/n4j/templates/neo4j-server-#{@server_version}.properties")).result
|
81
|
+
neo4j_server_properties_path = "#{neo4j_home}/neo4j-server.properties"
|
82
|
+
File.open(neo4j_server_properties_path, 'w') {|f| f.write(neo4j_server_properties) }
|
83
|
+
|
84
|
+
neo4j_wrapper_conf = "##### Genereated file! May be overwritten. ##### \n" +
|
85
|
+
ERB.new(IO.read('lib/n4j/templates/neo4j-wrapper.conf')).result
|
86
|
+
neo4j_wrapper_conf_path = "#{neo4j_home}/neo4j-wrapper.conf"
|
87
|
+
File.open(neo4j_wrapper_conf_path, 'w') {|f| f.write(neo4j_wrapper_conf) }
|
88
|
+
|
89
|
+
launch_neo4j_command = "#{java_command}
|
90
|
+
-cp #{class_path}
|
91
|
+
-server
|
92
|
+
-XX:+DisableExplicitGC
|
93
|
+
-Dorg.neo4j.server.properties=#{neo4j_server_properties_path}
|
94
|
+
-Djava.util.logging.config.file=#{neo4j_home}/logging.properties
|
95
|
+
-Xms3m
|
96
|
+
-Xmx64m
|
97
|
+
-Dlog4j.configuration=file:#{neo4j_home}/log4j.properties
|
98
|
+
-Dorg.neo4j.server.properties=#{neo4j_server_properties_path}
|
99
|
+
-Djava.util.logging.config.file=#{neo4j_home}/logging.properties
|
100
|
+
-Dneo4j.home=#{neo4j_home}
|
101
|
+
-Dneo4j.instance=#{libexec} org.neo4j.server.Bootstrapper
|
102
|
+
>> #{neo4j_home}/data/log/console.log 2>&1 & echo $! > \"#{pid_file}\"
|
103
|
+
"
|
104
|
+
# puts launch_neo4j_command
|
105
|
+
system launch_neo4j_command.gsub(/\n/,' ').gsub(/\s+/, ' ')
|
106
|
+
puts "#{environment.capitalize} Neo4j launched."
|
107
|
+
|
108
|
+
end
|
109
|
+
end
|
110
|
+
|
111
|
+
desc "Stop server"
|
112
|
+
task :stop do
|
113
|
+
YAML.parse_file('config/n4j.yml').to_ruby.each_pair do |environment, conf|
|
114
|
+
pid = IO.read "tmp/pids/n4j_#{environment}_pid"
|
115
|
+
pid.chomp!
|
116
|
+
result = `ps p#{pid} | grep #{pid} | wc -l`
|
117
|
+
if result.to_i > 0
|
118
|
+
Process.kill("HUP", pid.to_i)
|
119
|
+
puts "Killed #{environment} Neo4j."
|
120
|
+
else
|
121
|
+
puts "#{environment.capitalize} Neo4j wasn't running."
|
122
|
+
end
|
123
|
+
end
|
124
|
+
end
|
125
|
+
end
|