ripple 0.9.5 → 1.0.0.beta
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 +32 -0
- data/Gemfile +10 -9
- data/Guardfile +15 -0
- data/Rakefile +11 -40
- data/lib/rails/generators/ripple/configuration/configuration_generator.rb +0 -13
- data/lib/rails/generators/ripple/configuration/templates/ripple.yml +4 -4
- data/lib/rails/generators/ripple/js/js_generator.rb +0 -13
- data/lib/rails/generators/ripple/js/templates/js/contrib.js +0 -17
- data/lib/rails/generators/ripple/js/templates/js/ripple.js +0 -13
- data/lib/rails/generators/ripple/model/model_generator.rb +0 -14
- data/lib/rails/generators/ripple/model/templates/model.rb +1 -1
- data/lib/rails/generators/ripple/observer/observer_generator.rb +0 -14
- data/lib/rails/generators/ripple/test/test_generator.rb +7 -19
- data/lib/rails/generators/ripple_generator.rb +1 -14
- data/lib/ripple.rb +7 -14
- data/lib/ripple/associations.rb +129 -26
- data/lib/ripple/associations/embedded.rb +1 -15
- data/lib/ripple/associations/instantiators.rb +0 -13
- data/lib/ripple/associations/linked.rb +41 -19
- data/lib/ripple/associations/many.rb +0 -14
- data/lib/ripple/associations/many_embedded_proxy.rb +0 -14
- data/lib/ripple/associations/many_linked_proxy.rb +39 -18
- data/lib/ripple/associations/many_reference_proxy.rb +93 -0
- data/lib/ripple/associations/many_stored_key_proxy.rb +76 -0
- data/lib/ripple/associations/one.rb +1 -15
- data/lib/ripple/associations/one_embedded_proxy.rb +0 -14
- data/lib/ripple/associations/one_key_proxy.rb +58 -0
- data/lib/ripple/associations/one_linked_proxy.rb +4 -14
- data/lib/ripple/associations/one_stored_key_proxy.rb +43 -0
- data/lib/ripple/associations/proxy.rb +8 -14
- data/lib/ripple/attribute_methods.rb +19 -17
- data/lib/ripple/attribute_methods/dirty.rb +19 -15
- data/lib/ripple/attribute_methods/query.rb +0 -14
- data/lib/ripple/attribute_methods/read.rb +0 -14
- data/lib/ripple/attribute_methods/write.rb +0 -14
- data/lib/ripple/callbacks.rb +10 -16
- data/lib/ripple/conflict/basic_resolver.rb +82 -0
- data/lib/ripple/conflict/document_hooks.rb +20 -0
- data/lib/ripple/conflict/resolver.rb +71 -0
- data/lib/ripple/conflict/test_helper.rb +33 -0
- data/lib/ripple/conversion.rb +0 -14
- data/lib/ripple/core_ext.rb +1 -14
- data/lib/ripple/core_ext/casting.rb +19 -19
- data/lib/ripple/core_ext/object.rb +8 -0
- data/lib/ripple/document.rb +21 -16
- data/lib/ripple/document/bucket_access.rb +0 -14
- data/lib/ripple/document/finders.rb +17 -23
- data/lib/ripple/document/key.rb +8 -28
- data/lib/ripple/document/link.rb +30 -0
- data/lib/ripple/document/persistence.rb +12 -20
- data/lib/ripple/embedded_document.rb +10 -15
- data/lib/ripple/embedded_document/around_callbacks.rb +18 -0
- data/lib/ripple/embedded_document/finders.rb +7 -18
- data/lib/ripple/embedded_document/persistence.rb +5 -17
- data/lib/ripple/i18n.rb +0 -14
- data/lib/ripple/inspection.rb +21 -15
- data/lib/ripple/locale/en.yml +9 -13
- data/lib/ripple/nested_attributes.rb +33 -39
- data/lib/ripple/observable.rb +0 -13
- data/lib/ripple/properties.rb +1 -14
- data/lib/ripple/property_type_mismatch.rb +0 -14
- data/lib/ripple/railtie.rb +4 -14
- data/lib/ripple/railties/ripple.rake +86 -0
- data/lib/ripple/serialization.rb +11 -11
- data/lib/ripple/test_server.rb +36 -0
- data/lib/ripple/timestamps.rb +0 -13
- data/lib/ripple/translation.rb +4 -14
- data/lib/ripple/validations.rb +1 -15
- data/lib/ripple/validations/associated_validator.rb +26 -17
- data/lib/ripple/version.rb +3 -0
- data/ripple.gemspec +24 -35
- data/spec/integration/ripple/associations_spec.rb +89 -58
- data/spec/integration/ripple/conflict_resolution_spec.rb +298 -0
- data/spec/integration/ripple/nested_attributes_spec.rb +19 -19
- data/spec/integration/ripple/persistence_spec.rb +15 -34
- data/spec/integration/ripple/search_associations_spec.rb +31 -0
- data/spec/ripple/associations/many_embedded_proxy_spec.rb +23 -36
- data/spec/ripple/associations/many_linked_proxy_spec.rb +133 -45
- data/spec/ripple/associations/many_reference_proxy_spec.rb +170 -0
- data/spec/ripple/associations/many_stored_key_proxy_spec.rb +158 -0
- data/spec/ripple/associations/one_embedded_proxy_spec.rb +24 -37
- data/spec/ripple/associations/one_key_proxy_spec.rb +82 -0
- data/spec/ripple/associations/one_linked_proxy_spec.rb +22 -23
- data/spec/ripple/associations/one_stored_key_proxy_spec.rb +72 -0
- data/spec/ripple/associations/proxy_spec.rb +21 -15
- data/spec/ripple/associations_spec.rb +54 -23
- data/spec/ripple/attribute_methods/dirty_spec.rb +56 -5
- data/spec/ripple/attribute_methods_spec.rb +47 -21
- data/spec/ripple/bucket_access_spec.rb +4 -17
- data/spec/ripple/callbacks_spec.rb +52 -15
- data/spec/ripple/conflict/resolver_spec.rb +42 -0
- data/spec/ripple/conversion_spec.rb +2 -15
- data/spec/ripple/core_ext_spec.rb +12 -15
- data/spec/ripple/document/link_spec.rb +67 -0
- data/spec/ripple/document_spec.rb +34 -19
- data/spec/ripple/embedded_document/finders_spec.rb +12 -19
- data/spec/ripple/embedded_document/persistence_spec.rb +20 -26
- data/spec/ripple/embedded_document_spec.rb +44 -34
- data/spec/ripple/finders_spec.rb +58 -29
- data/spec/ripple/inspection_spec.rb +40 -37
- data/spec/ripple/key_spec.rb +5 -17
- data/spec/ripple/observable_spec.rb +3 -16
- data/spec/ripple/persistence_spec.rb +134 -18
- data/spec/ripple/properties_spec.rb +21 -15
- data/spec/ripple/ripple_spec.rb +1 -14
- data/spec/ripple/serialization_spec.rb +16 -17
- data/spec/ripple/timestamps_spec.rb +73 -52
- data/spec/ripple/validations/associated_validator_spec.rb +69 -25
- data/spec/ripple/validations_spec.rb +3 -16
- data/spec/spec_helper.rb +17 -18
- data/spec/support/associations.rb +1 -1
- data/spec/support/associations/proxies.rb +0 -13
- data/spec/support/integration_setup.rb +11 -0
- data/spec/support/mocks.rb +0 -13
- data/spec/support/models.rb +33 -2
- data/spec/support/models/address.rb +1 -16
- data/spec/support/models/box.rb +7 -14
- data/spec/support/models/car.rb +27 -1
- data/spec/support/models/cardboard_box.rb +0 -14
- data/spec/support/models/clock.rb +6 -15
- data/spec/support/models/clock_observer.rb +0 -14
- data/spec/support/models/credit_card.rb +5 -0
- data/spec/support/models/customer.rb +0 -14
- data/spec/support/models/email.rb +0 -14
- data/spec/support/models/family.rb +1 -13
- data/spec/support/models/favorite.rb +0 -14
- data/spec/support/models/invoice.rb +0 -14
- data/spec/support/models/late_invoice.rb +0 -14
- data/spec/support/models/nested.rb +12 -0
- data/spec/support/models/ninja.rb +7 -0
- data/spec/support/models/note.rb +0 -14
- data/spec/support/models/page.rb +1 -15
- data/spec/support/models/paid_invoice.rb +0 -14
- data/spec/support/models/post.rb +12 -0
- data/spec/support/models/profile.rb +7 -0
- data/spec/support/models/subscription.rb +26 -0
- data/spec/support/models/tasks.rb +0 -18
- data/spec/support/models/team.rb +11 -0
- data/spec/support/models/transactions.rb +17 -0
- data/spec/support/models/tree.rb +2 -16
- data/spec/support/models/user.rb +14 -16
- data/spec/support/models/widget.rb +8 -14
- data/spec/support/search.rb +14 -0
- data/spec/support/test_server.rb +22 -12
- data/spec/support/test_server.yml.example +14 -2
- metadata +223 -59
- data/lib/rails/generators/ripple/test/templates/test_server.rb +0 -46
- data/spec/support/models/driver.rb +0 -5
- data/spec/support/models/engine.rb +0 -4
- data/spec/support/models/passenger.rb +0 -5
- data/spec/support/models/seat.rb +0 -4
- data/spec/support/models/wheel.rb +0 -5
data/.gitignore
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
## MAC OS
|
|
2
|
+
.DS_Store
|
|
3
|
+
|
|
4
|
+
## TEXTMATE
|
|
5
|
+
*.tmproj
|
|
6
|
+
tmtags
|
|
7
|
+
|
|
8
|
+
## EMACS
|
|
9
|
+
*~
|
|
10
|
+
\#*
|
|
11
|
+
.\#*
|
|
12
|
+
|
|
13
|
+
## VIM
|
|
14
|
+
*.swp
|
|
15
|
+
|
|
16
|
+
## PROJECT::GENERAL
|
|
17
|
+
coverage/**/*
|
|
18
|
+
rdoc/**/*
|
|
19
|
+
pkg/**/*
|
|
20
|
+
|
|
21
|
+
## PROJECT::SPECIFIC
|
|
22
|
+
doc/*
|
|
23
|
+
.yardoc
|
|
24
|
+
.bundle
|
|
25
|
+
spec/support/test_server.yml
|
|
26
|
+
Gemfile.lock
|
|
27
|
+
**/bin
|
|
28
|
+
*.rbc
|
|
29
|
+
.rvmrc
|
|
30
|
+
|
|
31
|
+
.ripplenode
|
|
32
|
+
.riaktest
|
data/Gemfile
CHANGED
|
@@ -1,16 +1,18 @@
|
|
|
1
1
|
source :rubygems
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
gem 'riak-client', :path => "../riak-client"
|
|
5
|
-
gem 'activemodel', '~>3.0.0'
|
|
6
|
-
gem 'rspec', '~>2.4.0'
|
|
7
|
-
gem 'tzinfo'
|
|
8
|
-
gem 'rake'
|
|
3
|
+
gemspec
|
|
9
4
|
|
|
10
|
-
|
|
11
|
-
gem '
|
|
5
|
+
if ENV['RAILS31']
|
|
6
|
+
gem 'activemodel', '~> 3.1.0'
|
|
7
|
+
else
|
|
8
|
+
gem 'activemodel', '~> 3.0.10'
|
|
12
9
|
end
|
|
13
10
|
|
|
11
|
+
gem 'riak-client', :path => "../riak-client"
|
|
12
|
+
gem 'guard-rspec'
|
|
13
|
+
gem 'rb-fsevent'
|
|
14
|
+
gem 'growl'
|
|
15
|
+
|
|
14
16
|
platforms :mri_18, :jruby do
|
|
15
17
|
gem 'ruby-debug'
|
|
16
18
|
end
|
|
@@ -20,6 +22,5 @@ platforms :mri_19 do
|
|
|
20
22
|
end
|
|
21
23
|
|
|
22
24
|
platforms :jruby do
|
|
23
|
-
gem 'json'
|
|
24
25
|
gem 'jruby-openssl'
|
|
25
26
|
end
|
data/Guardfile
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# A sample Guardfile
|
|
2
|
+
# More info at https://github.com/guard/guard#readme
|
|
3
|
+
gemset = ENV['RVM_GEMSET'] || 'ripple'
|
|
4
|
+
gemset = "@#{gemset}" unless gemset.to_s == ''
|
|
5
|
+
|
|
6
|
+
rvms = %w[ 1.8.7 1.9.2 jruby ].map do |version|
|
|
7
|
+
"#{version}@#{gemset}"
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
guard 'rspec', :cli => '--profile', :rvm => rvms do
|
|
11
|
+
watch(%r{^spec/.+_spec\.rb$})
|
|
12
|
+
watch(%r{^lib/(.+)\.rb$}) { |m| "spec/#{m[1]}_spec.rb" }
|
|
13
|
+
watch('spec/spec_helper.rb') { "spec/ripple" }
|
|
14
|
+
end
|
|
15
|
+
|
data/Rakefile
CHANGED
|
@@ -1,48 +1,22 @@
|
|
|
1
1
|
require 'rubygems'
|
|
2
|
-
require '
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
gemspec = Gem::Specification.new do |gem|
|
|
7
|
-
gem.name = "ripple"
|
|
8
|
-
gem.summary = %Q{ripple is an object-mapper library for Riak, the distributed database by Basho.}
|
|
9
|
-
gem.description = %Q{ripple is an object-mapper library for Riak, the distributed database by Basho. It uses ActiveModel to provide an experience that integrates well with Rails 3 applications.}
|
|
10
|
-
gem.version = version
|
|
11
|
-
gem.email = "sean@basho.com"
|
|
12
|
-
gem.homepage = "http://seancribbs.github.com/ripple"
|
|
13
|
-
gem.authors = ["Sean Cribbs"]
|
|
14
|
-
gem.add_development_dependency "rspec", "~>2.4.0"
|
|
15
|
-
gem.add_dependency "riak-client", "~>#{version}"
|
|
16
|
-
gem.add_dependency "activesupport", "~>3.0.0"
|
|
17
|
-
gem.add_dependency "activemodel", "~>3.0.0"
|
|
18
|
-
|
|
19
|
-
files = FileList["**/*"]
|
|
20
|
-
# Editor and O/S files
|
|
21
|
-
files.exclude ".DS_Store", "*~", "\#*", ".\#*", "*.swp", "*.tmproj", "tmtags"
|
|
22
|
-
# Generated artifacts
|
|
23
|
-
files.exclude "coverage", "rdoc", "pkg", ".bundle", "*.rbc", ".rvmrc", ".watchr", ".rspec"
|
|
24
|
-
# Project-specific
|
|
25
|
-
files.exclude "Gemfile.lock", %r{spec/support/test_server.yml$}, "bin"
|
|
26
|
-
# Remove directories
|
|
27
|
-
files.exclude {|d| File.directory?(d) }
|
|
28
|
-
|
|
29
|
-
gem.files = files.to_a
|
|
2
|
+
require 'rubygems/package_task'
|
|
3
|
+
require 'rspec/core'
|
|
4
|
+
require 'rspec/core/rake_task'
|
|
30
5
|
|
|
31
|
-
|
|
6
|
+
def gemspec
|
|
7
|
+
$ripple_gemspec ||= Gem::Specification.load("ripple.gemspec")
|
|
32
8
|
end
|
|
33
9
|
|
|
34
|
-
|
|
35
|
-
Rake::GemPackageTask.new(gemspec) do |pkg|
|
|
10
|
+
Gem::PackageTask.new(gemspec) do |pkg|
|
|
36
11
|
pkg.need_zip = false
|
|
37
12
|
pkg.need_tar = false
|
|
38
13
|
end
|
|
39
14
|
|
|
40
15
|
task :gem => :gemspec
|
|
41
16
|
|
|
42
|
-
desc %{
|
|
17
|
+
desc %{Validate the gemspec file.}
|
|
43
18
|
task :gemspec do
|
|
44
19
|
gemspec.validate
|
|
45
|
-
File.open("#{gemspec.name}.gemspec", 'w'){|f| f.write gemspec.to_ruby }
|
|
46
20
|
end
|
|
47
21
|
|
|
48
22
|
desc %{Release the gem to RubyGems.org}
|
|
@@ -50,24 +24,21 @@ task :release => :gem do
|
|
|
50
24
|
system "gem push pkg/#{gemspec.name}-#{gemspec.version}.gem"
|
|
51
25
|
end
|
|
52
26
|
|
|
53
|
-
require 'rspec/core'
|
|
54
|
-
require 'rspec/core/rake_task'
|
|
55
|
-
|
|
56
27
|
desc "Run Unit Specs Only"
|
|
57
28
|
RSpec::Core::RakeTask.new(:spec) do |spec|
|
|
58
|
-
spec.
|
|
29
|
+
spec.rspec_opts = %w[--profile --tag ~integration]
|
|
59
30
|
end
|
|
60
31
|
|
|
61
32
|
namespace :spec do
|
|
62
33
|
desc "Run Integration Specs Only"
|
|
63
34
|
RSpec::Core::RakeTask.new(:integration) do |spec|
|
|
64
|
-
spec.
|
|
35
|
+
spec.rspec_opts = %w[--profile --tag integration]
|
|
65
36
|
end
|
|
66
37
|
|
|
67
38
|
desc "Run All Specs"
|
|
68
39
|
RSpec::Core::RakeTask.new(:all) do |spec|
|
|
69
|
-
spec.
|
|
40
|
+
spec.rspec_opts = %w[--profile]
|
|
70
41
|
end
|
|
71
42
|
end
|
|
72
43
|
|
|
73
|
-
task :default => :
|
|
44
|
+
task :default => "spec:all"
|
|
@@ -1,16 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
1
|
require 'rails/generators/ripple_generator'
|
|
15
2
|
|
|
16
3
|
module Ripple
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
development:
|
|
3
3
|
http_port: 8098
|
|
4
4
|
pb_port: 8087
|
|
5
|
-
host:
|
|
5
|
+
host: 127.0.0.1
|
|
6
6
|
|
|
7
7
|
# The test environment has additional keys for configuring the
|
|
8
8
|
# Riak::TestServer for your test/spec suite:
|
|
@@ -14,11 +14,11 @@ development:
|
|
|
14
14
|
test:
|
|
15
15
|
http_port: 9000
|
|
16
16
|
pb_port: 9002
|
|
17
|
-
host:
|
|
18
|
-
|
|
17
|
+
host: 127.0.0.1
|
|
18
|
+
source: /usr/local/bin # Default for Homebrew.
|
|
19
19
|
js_source_dir: <%%= Rails.root + "app/mapreduce" %>
|
|
20
20
|
|
|
21
21
|
production:
|
|
22
22
|
http_port: 8098
|
|
23
23
|
pb_port: 8087
|
|
24
|
-
host:
|
|
24
|
+
host: 127.0.0.1
|
|
@@ -1,16 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
1
|
require 'rails/generators/ripple_generator'
|
|
15
2
|
|
|
16
3
|
module Ripple
|
|
@@ -1,22 +1,5 @@
|
|
|
1
1
|
// -------------------------------------------------------------------
|
|
2
2
|
//
|
|
3
|
-
//
|
|
4
|
-
// This file is provided to you under the Apache License,
|
|
5
|
-
// Version 2.0 (the "License"); you may not use this file
|
|
6
|
-
// except in compliance with the License. You may obtain
|
|
7
|
-
// a copy of the License at
|
|
8
|
-
//
|
|
9
|
-
// http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
-
//
|
|
11
|
-
// Unless required by applicable law or agreed to in writing,
|
|
12
|
-
// software distributed under the License is distributed on an
|
|
13
|
-
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
|
14
|
-
// KIND, either express or implied. See the License for the
|
|
15
|
-
// specific language governing permissions and limitations
|
|
16
|
-
// under the License.
|
|
17
|
-
//
|
|
18
|
-
// -------------------------------------------------------------------
|
|
19
|
-
//
|
|
20
3
|
// This file contains Javascript MapReduce functions copied from the
|
|
21
4
|
// "Riak Function Contrib" project.
|
|
22
5
|
//
|
|
@@ -1,16 +1,3 @@
|
|
|
1
|
-
// Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
//
|
|
3
|
-
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
// you may not use this file except in compliance with the License.
|
|
5
|
-
// You may obtain a copy of the License at
|
|
6
|
-
//
|
|
7
|
-
// http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
//
|
|
9
|
-
// Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
// See the License for the specific language governing permissions and
|
|
13
|
-
// limitations under the License.
|
|
14
1
|
|
|
15
2
|
/*
|
|
16
3
|
* Namespace for Ripple's built-in MapReduce functions.
|
|
@@ -1,17 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
|
-
|
|
15
1
|
require 'rails/generators/ripple_generator'
|
|
16
2
|
|
|
17
3
|
module Ripple
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
class <%= class_name %><%= " < #{options[:parent].classify}" if options[:parent] %>
|
|
2
2
|
<% unless options[:parent] -%>
|
|
3
3
|
include Ripple::<%= "Embedded" if options[:embedded] || options[:embedded_in] %>Document
|
|
4
|
-
<% if options[:embedded_in] -%>embedded_in :<%= options[:embedded_in].underscore %><% end -%>
|
|
4
|
+
<% if options[:embedded_in] -%>embedded_in :<%= options[:embedded_in].underscore %><% end -%>
|
|
5
5
|
<% end -%>
|
|
6
6
|
|
|
7
7
|
<% attributes.reject{|attr| attr.reference?}.each do |attribute| -%>
|
|
@@ -1,17 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
|
-
|
|
15
1
|
require 'rails/generators/ripple_generator'
|
|
16
2
|
|
|
17
3
|
module Ripple
|
|
@@ -1,16 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
1
|
require 'rails/generators/ripple_generator'
|
|
15
2
|
|
|
16
3
|
module Ripple
|
|
@@ -20,7 +7,6 @@ module Ripple
|
|
|
20
7
|
# Cucumber
|
|
21
8
|
def create_cucumber_file
|
|
22
9
|
if File.directory?(Rails.root + "features/support")
|
|
23
|
-
template 'test_server.rb', 'features/support/ripple.rb'
|
|
24
10
|
insert_into_file 'features/support/ripple.rb', "\n\nAfter do\n Ripple::TestServer.clear\nend", :after => "Ripple::TestServer.setup"
|
|
25
11
|
end
|
|
26
12
|
end
|
|
@@ -28,9 +14,12 @@ module Ripple
|
|
|
28
14
|
# RSpec
|
|
29
15
|
def create_rspec_file
|
|
30
16
|
if File.file?(Rails.root + 'spec/spec_helper.rb')
|
|
31
|
-
|
|
17
|
+
inject_into_file 'spec/spec_helper.rb', :before => /R[Ss]pec\.configure do \|config\|/ do
|
|
18
|
+
"require 'ripple/test_server'\n"
|
|
19
|
+
end
|
|
32
20
|
inject_into_file 'spec/spec_helper.rb', :after => /R[Ss]pec\.configure do \|config\|/ do
|
|
33
|
-
"\n config.
|
|
21
|
+
"\n config.before(:all){ Ripple::TestServer.setup }" +
|
|
22
|
+
"\n config.after(:each){ Ripple::TestServer.clear }\n"
|
|
34
23
|
end
|
|
35
24
|
end
|
|
36
25
|
end
|
|
@@ -38,12 +27,11 @@ module Ripple
|
|
|
38
27
|
# Test::Unit
|
|
39
28
|
def create_test_unit_file
|
|
40
29
|
if File.file?(Rails.root + 'test/test_helper.rb')
|
|
41
|
-
template 'test_server.rb', 'test/ripple_test_helper.rb'
|
|
42
30
|
inject_into_file "test/test_helper.rb", :before => "class ActiveSupport::TestCase" do
|
|
43
|
-
"# Setup in-memory test server for Riak\nrequire
|
|
31
|
+
"# Setup in-memory test server for Riak\nrequire 'ripple/test_server'\n\n"
|
|
44
32
|
end
|
|
45
33
|
inject_into_class "test/test_helper.rb", ActiveSupport::TestCase do
|
|
46
|
-
" teardown { Ripple::TestServer.clear }\n\n"
|
|
34
|
+
" setup { Ripple::TestServer.setup }\n teardown { Ripple::TestServer.clear }\n\n"
|
|
47
35
|
end
|
|
48
36
|
end
|
|
49
37
|
end
|
|
@@ -1,16 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
1
|
require "rails/generators/named_base"
|
|
15
2
|
require "rails/generators/active_model"
|
|
16
3
|
|
|
@@ -43,7 +30,7 @@ module Ripple
|
|
|
43
30
|
# Generator for a {Ripple::Document} model
|
|
44
31
|
class ActiveModel < ::Rails::Generators::ActiveModel
|
|
45
32
|
def self.all(klass)
|
|
46
|
-
"#{klass}.
|
|
33
|
+
"#{klass}.list"
|
|
47
34
|
end
|
|
48
35
|
|
|
49
36
|
def self.find(klass, params=nil)
|
data/lib/ripple.rb
CHANGED
|
@@ -1,17 +1,3 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
|
-
|
|
15
1
|
require 'riak'
|
|
16
2
|
require 'erb'
|
|
17
3
|
require 'yaml'
|
|
@@ -68,6 +54,7 @@ module Ripple
|
|
|
68
54
|
config_file = File.expand_path(config_file)
|
|
69
55
|
config_hash = YAML.load(ERB.new(File.read(config_file)).result).with_indifferent_access
|
|
70
56
|
config_keys.each {|k| config_hash = config_hash[k]}
|
|
57
|
+
configure_ports(config_hash)
|
|
71
58
|
self.config = config_hash || {}
|
|
72
59
|
rescue Errno::ENOENT
|
|
73
60
|
raise Ripple::MissingConfiguration.new(config_file)
|
|
@@ -78,6 +65,12 @@ module Ripple
|
|
|
78
65
|
def client_config
|
|
79
66
|
config.slice(*Riak::Client::VALID_OPTIONS)
|
|
80
67
|
end
|
|
68
|
+
|
|
69
|
+
def configure_ports(config)
|
|
70
|
+
return unless config && config[:min_port]
|
|
71
|
+
config[:http_port] ||= (config[:min_port].to_i)
|
|
72
|
+
config[:pb_port] ||= (config[:min_port].to_i + 1)
|
|
73
|
+
end
|
|
81
74
|
end
|
|
82
75
|
|
|
83
76
|
# Exception raised when the path passed to
|
data/lib/ripple/associations.rb
CHANGED
|
@@ -1,18 +1,5 @@
|
|
|
1
|
-
# Copyright 2010 Sean Cribbs, Sonian Inc., and Basho Technologies, Inc.
|
|
2
|
-
#
|
|
3
|
-
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
-
# you may not use this file except in compliance with the License.
|
|
5
|
-
# You may obtain a copy of the License at
|
|
6
|
-
#
|
|
7
|
-
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
-
#
|
|
9
|
-
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
-
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
-
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
-
# See the License for the specific language governing permissions and
|
|
13
|
-
# limitations under the License.
|
|
14
|
-
|
|
15
1
|
require 'active_support/concern'
|
|
2
|
+
require 'active_support/dependencies'
|
|
16
3
|
require 'riak/walk_spec'
|
|
17
4
|
require 'ripple/translation'
|
|
18
5
|
require 'ripple/associations/proxy'
|
|
@@ -26,11 +13,15 @@ require 'ripple/associations/one_embedded_proxy'
|
|
|
26
13
|
require 'ripple/associations/many_embedded_proxy'
|
|
27
14
|
require 'ripple/associations/one_linked_proxy'
|
|
28
15
|
require 'ripple/associations/many_linked_proxy'
|
|
16
|
+
require 'ripple/associations/many_stored_key_proxy'
|
|
17
|
+
require 'ripple/associations/one_key_proxy'
|
|
18
|
+
require 'ripple/associations/one_stored_key_proxy'
|
|
19
|
+
require 'ripple/associations/many_reference_proxy'
|
|
29
20
|
|
|
30
21
|
module Ripple
|
|
31
22
|
# Adds associations via links and embedding to {Ripple::Document}
|
|
32
23
|
# models. Examples:
|
|
33
|
-
#
|
|
24
|
+
#
|
|
34
25
|
# # Documents can contain embedded documents, and link to other standalone documents
|
|
35
26
|
# # via associations using the many and one class methods.
|
|
36
27
|
# class Person
|
|
@@ -40,14 +31,14 @@ module Ripple
|
|
|
40
31
|
# many :friends, :class_name => "Person"
|
|
41
32
|
# one :account
|
|
42
33
|
# end
|
|
43
|
-
#
|
|
34
|
+
#
|
|
44
35
|
# # Account and Address are embeddable documents
|
|
45
36
|
# class Account
|
|
46
37
|
# include Ripple::EmbeddedDocument
|
|
47
38
|
# property :paid_until, Time
|
|
48
39
|
# embedded_in :person # Adds "person" method to get parent document
|
|
49
40
|
# end
|
|
50
|
-
#
|
|
41
|
+
#
|
|
51
42
|
# class Address
|
|
52
43
|
# include Ripple::EmbeddedDocument
|
|
53
44
|
# property :street, String
|
|
@@ -55,7 +46,7 @@ module Ripple
|
|
|
55
46
|
# property :state, String
|
|
56
47
|
# property :zip, String
|
|
57
48
|
# end
|
|
58
|
-
#
|
|
49
|
+
#
|
|
59
50
|
# person = Person.find("adamhunter")
|
|
60
51
|
# person.friends << Person.find("seancribbs") # Links to people/seancribbs with tag "friend"
|
|
61
52
|
# person.addresses << Address.new(:street => "100 Main Street") # Adds an embedded address
|
|
@@ -64,6 +55,7 @@ module Ripple
|
|
|
64
55
|
extend ActiveSupport::Concern
|
|
65
56
|
|
|
66
57
|
module ClassMethods
|
|
58
|
+
include Translation
|
|
67
59
|
# @private
|
|
68
60
|
def inherited(subclass)
|
|
69
61
|
super
|
|
@@ -77,22 +69,39 @@ module Ripple
|
|
|
77
69
|
|
|
78
70
|
# Associations of embedded documents
|
|
79
71
|
def embedded_associations
|
|
80
|
-
associations.values.select(&:
|
|
72
|
+
associations.values.select(&:embedded?)
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# Associations of linked documents
|
|
76
|
+
def linked_associations
|
|
77
|
+
associations.values.select(&:linked?)
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
# Associations of stored_key documents
|
|
81
|
+
def stored_key_associations
|
|
82
|
+
associations.values.select(&:stored_key?)
|
|
81
83
|
end
|
|
82
84
|
|
|
83
85
|
# Creates a singular association
|
|
84
86
|
def one(name, options={})
|
|
87
|
+
configure_for_key_correspondence if options[:using] === :key
|
|
85
88
|
create_association(:one, name, options)
|
|
86
89
|
end
|
|
87
90
|
|
|
88
91
|
# Creates a plural association
|
|
89
92
|
def many(name, options={})
|
|
93
|
+
raise ArgumentError, t('many_key_association') if options[:using] === :key
|
|
90
94
|
create_association(:many, name, options)
|
|
91
95
|
end
|
|
92
96
|
|
|
97
|
+
def configure_for_key_correspondence
|
|
98
|
+
include Ripple::Associations::KeyDelegator
|
|
99
|
+
end
|
|
100
|
+
|
|
93
101
|
private
|
|
94
102
|
def create_association(type, name, options={})
|
|
95
103
|
association = associations[name] = Association.new(type, name, options)
|
|
104
|
+
association.setup_on(self)
|
|
96
105
|
|
|
97
106
|
define_method(name) do
|
|
98
107
|
get_proxy(association)
|
|
@@ -121,6 +130,13 @@ module Ripple
|
|
|
121
130
|
proxy
|
|
122
131
|
end
|
|
123
132
|
|
|
133
|
+
# @private
|
|
134
|
+
def reset_associations
|
|
135
|
+
self.class.associations.each do |name, assoc_object|
|
|
136
|
+
send(name).reset
|
|
137
|
+
end
|
|
138
|
+
end
|
|
139
|
+
|
|
124
140
|
# Adds embedded documents to the attributes
|
|
125
141
|
# @private
|
|
126
142
|
def attributes_for_persistence
|
|
@@ -137,6 +153,39 @@ module Ripple
|
|
|
137
153
|
attrs
|
|
138
154
|
end
|
|
139
155
|
end
|
|
156
|
+
|
|
157
|
+
def propagate_callbacks_to_embedded_associations(name, kind)
|
|
158
|
+
self.class.embedded_associations.each do |association|
|
|
159
|
+
documents = instance_variable_get(association.ivar)
|
|
160
|
+
# We must explicitly check #nil? (rather than just saying `if documents`)
|
|
161
|
+
# because documents can be an association proxy that is proxying nil.
|
|
162
|
+
# In this case ruby treats documents as true because it is not _really_ nil,
|
|
163
|
+
# but #nil? will tell us if it is proxying nil.
|
|
164
|
+
next if documents.nil?
|
|
165
|
+
|
|
166
|
+
Array(documents).each do |doc|
|
|
167
|
+
doc.send("_#{name}_callbacks").each do |callback|
|
|
168
|
+
next unless callback.kind == kind
|
|
169
|
+
doc.send(callback.filter)
|
|
170
|
+
end
|
|
171
|
+
end
|
|
172
|
+
end
|
|
173
|
+
end
|
|
174
|
+
|
|
175
|
+
# Propagates callbacks (save/create/update/destroy) to embedded associated documents.
|
|
176
|
+
# This is necessary so that when a parent is saved, the embedded child's before_save
|
|
177
|
+
# hooks are run as well.
|
|
178
|
+
# @private
|
|
179
|
+
def run_callbacks(name, *args, &block)
|
|
180
|
+
# validation is already propagated to embedded documents via the
|
|
181
|
+
# AssociatedValidator. We don't need to duplicate the propgation here.
|
|
182
|
+
return super if name == :validation
|
|
183
|
+
|
|
184
|
+
propagate_callbacks_to_embedded_associations(name, :before)
|
|
185
|
+
return_value = super
|
|
186
|
+
propagate_callbacks_to_embedded_associations(name, :after)
|
|
187
|
+
return_value
|
|
188
|
+
end
|
|
140
189
|
end
|
|
141
190
|
end
|
|
142
191
|
|
|
@@ -169,7 +218,7 @@ module Ripple
|
|
|
169
218
|
|
|
170
219
|
# @return [Class] The class of the associated object(s)
|
|
171
220
|
def klass
|
|
172
|
-
@klass ||=
|
|
221
|
+
@klass ||= discover_class
|
|
173
222
|
end
|
|
174
223
|
|
|
175
224
|
# @return [true,false] Is the cardinality of the association > 1
|
|
@@ -183,7 +232,7 @@ module Ripple
|
|
|
183
232
|
end
|
|
184
233
|
|
|
185
234
|
# @return [true,false] Is the associated class an EmbeddedDocument
|
|
186
|
-
def
|
|
235
|
+
def embedded?
|
|
187
236
|
klass.embeddable?
|
|
188
237
|
end
|
|
189
238
|
|
|
@@ -198,6 +247,11 @@ module Ripple
|
|
|
198
247
|
using == :linked
|
|
199
248
|
end
|
|
200
249
|
|
|
250
|
+
# @return [true,false] Does the association use stored_key
|
|
251
|
+
def stored_key?
|
|
252
|
+
using == :stored_key
|
|
253
|
+
end
|
|
254
|
+
|
|
201
255
|
# @return [String] the instance variable in the owner where the association will be stored
|
|
202
256
|
def ivar
|
|
203
257
|
"@_#{name}"
|
|
@@ -224,13 +278,16 @@ module Ripple
|
|
|
224
278
|
linked? ? Array(link_spec).first.tag : nil
|
|
225
279
|
end
|
|
226
280
|
|
|
281
|
+
def bucket_name
|
|
282
|
+
polymorphic? ? '_' : klass.bucket_name
|
|
283
|
+
end
|
|
284
|
+
|
|
227
285
|
# @return [Riak::WalkSpec] when #linked? is true, a specification for which links to follow to retrieve the associated documents
|
|
228
286
|
def link_spec
|
|
229
287
|
# TODO: support transitive linked associations
|
|
230
288
|
if linked?
|
|
231
289
|
tag = name.to_s
|
|
232
|
-
|
|
233
|
-
Riak::WalkSpec.new(:tag => tag, :bucket => bucket)
|
|
290
|
+
Riak::WalkSpec.new(:tag => tag, :bucket => bucket_name)
|
|
234
291
|
else
|
|
235
292
|
nil
|
|
236
293
|
end
|
|
@@ -238,7 +295,7 @@ module Ripple
|
|
|
238
295
|
|
|
239
296
|
# @return [Symbol] which method is used for representing the association - currently only supports :embedded and :linked
|
|
240
297
|
def using
|
|
241
|
-
@using ||= options[:using] || (
|
|
298
|
+
@using ||= options[:using] || (embedded? ? :embedded : :linked)
|
|
242
299
|
end
|
|
243
300
|
|
|
244
301
|
# @raise [ArgumentError] if the value does not match the class of the association
|
|
@@ -258,10 +315,56 @@ module Ripple
|
|
|
258
315
|
when polymorphic?
|
|
259
316
|
one? || Array === value
|
|
260
317
|
when many?
|
|
261
|
-
Array === value && value.all? {|d| (
|
|
318
|
+
Array === value && value.all? {|d| (embedded? && Hash === d) || klass === d }
|
|
262
319
|
when one?
|
|
263
|
-
value.nil? || (
|
|
320
|
+
value.nil? || (embedded? && Hash === value) || value.kind_of?(klass)
|
|
321
|
+
end
|
|
322
|
+
end
|
|
323
|
+
|
|
324
|
+
def uses_search?
|
|
325
|
+
(options[:using] == :reference)
|
|
326
|
+
end
|
|
327
|
+
|
|
328
|
+
def setup_on(model)
|
|
329
|
+
@model = model
|
|
330
|
+
define_callbacks_on(model)
|
|
331
|
+
if uses_search?
|
|
332
|
+
klass.before_save do |o|
|
|
333
|
+
unless o.class.bucket.is_indexed?
|
|
334
|
+
o.class.bucket.enable_index!
|
|
335
|
+
end
|
|
336
|
+
end
|
|
264
337
|
end
|
|
265
338
|
end
|
|
339
|
+
|
|
340
|
+
def define_callbacks_on(klass)
|
|
341
|
+
_association = self
|
|
342
|
+
|
|
343
|
+
klass.before_save do
|
|
344
|
+
if _association.linked? && !@_in_save_loaded_documents_callback
|
|
345
|
+
@_in_save_loaded_documents_callback = true
|
|
346
|
+
|
|
347
|
+
begin
|
|
348
|
+
send(_association.name).loaded_documents.each do |document|
|
|
349
|
+
document.save if document.new? || document.changed?
|
|
350
|
+
end
|
|
351
|
+
ensure
|
|
352
|
+
remove_instance_variable(:@_in_save_loaded_documents_callback)
|
|
353
|
+
end
|
|
354
|
+
end
|
|
355
|
+
end
|
|
356
|
+
end
|
|
357
|
+
|
|
358
|
+
private
|
|
359
|
+
def discover_class
|
|
360
|
+
options[:class] || (@model && find_class(@model, class_name)) || class_name.constantize
|
|
361
|
+
end
|
|
362
|
+
|
|
363
|
+
def find_class(scope, class_name)
|
|
364
|
+
return nil if class_name.include?("::")
|
|
365
|
+
class_sym = class_name.to_sym
|
|
366
|
+
parent_scope = scope.parents.unshift(scope).find {|s| ActiveSupport::Dependencies.local_const_defined?(s, class_sym) }
|
|
367
|
+
parent_scope.const_get(class_sym) if parent_scope
|
|
368
|
+
end
|
|
266
369
|
end
|
|
267
370
|
end
|