activefacts-api 0.9.7 → 0.9.8
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.
- checksums.yaml +7 -0
- data/.travis.yml +1 -0
- data/Gemfile +4 -2
- data/Rakefile +19 -1
- data/VERSION +1 -1
- data/activefacts-api.gemspec +7 -7
- data/lib/activefacts/api/constellation.rb +8 -1
- data/lib/activefacts/api/entity.rb +11 -3
- data/lib/activefacts/api/exceptions.rb +3 -3
- data/lib/activefacts/api/guid.rb +5 -1
- data/lib/activefacts/api/instance.rb +13 -7
- data/lib/activefacts/api/instance_index.rb +1 -0
- data/lib/activefacts/api/object_type.rb +7 -14
- data/lib/activefacts/api/role_values.rb +74 -23
- data/lib/activefacts/api/standard_types.rb +1 -1
- data/lib/activefacts/api/support.rb +1 -3
- data/lib/activefacts/api/value.rb +2 -2
- data/lib/activefacts/api/vocabulary.rb +7 -6
- data/lib/activefacts/tracer.rb +1 -1
- data/spec/constellation/constellation_spec.rb +11 -11
- data/spec/constellation/instance_spec.rb +4 -4
- data/spec/fact_type/roles_spec.rb +29 -0
- data/spec/identification_scheme/identification_spec.rb +5 -4
- data/spec/identification_scheme/identity_supertype_change_spec.rb +2 -2
- data/spec/object_type/entity_type/entity_type_spec.rb +13 -13
- data/spec/object_type/entity_type/multipart_identification_spec.rb +1 -1
- data/spec/object_type/value_type/autocounter_spec.rb +3 -3
- data/spec/object_type/value_type/guid_spec.rb +1 -1
- data/spec/object_type/value_type/value_type_spec.rb +1 -1
- metadata +26 -61
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: dc17ae7a132478e2e4b591e19adf35d79627d70b
|
4
|
+
data.tar.gz: b6b63e83981a4ec466aa128b94fb7cfbf1370d0e
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 916183df4492dab5a94c172d85f58b7f4a04f8407eb9decc301b07c8f137a5c6b3bfd4c80ce4f4d7b98e5ba9fe26d0483dd3a71b768159701b63d0c07b3a0b1e
|
7
|
+
data.tar.gz: 14858f846fe7c1fba970cd1b2cd6f890d21ae5247ce2107d73c49e75d919cf011814bd724e8b90ace9fdd524b262a3c83538b242137452d13eb8c0f454758323
|
data/.travis.yml
CHANGED
data/Gemfile
CHANGED
@@ -1,13 +1,15 @@
|
|
1
1
|
source 'https://rubygems.org'
|
2
2
|
|
3
|
-
gem 'rake', :group => [:development, :test]
|
3
|
+
gem 'rake', '>=10.1', :group => [:development, :test]
|
4
4
|
gem 'rbtree-pure'
|
5
5
|
|
6
6
|
group :development do
|
7
7
|
gem 'jeweler'
|
8
8
|
gem 'rspec', '~>2.6.0'
|
9
9
|
gem 'ruby-debug', :platforms => [:mri_18]
|
10
|
-
gem 'debugger', :platforms => [:mri_19
|
10
|
+
gem 'debugger', :platforms => [:mri_19,
|
11
|
+
(['1.8.7', '1.9.2'].include?(RUBY_VERSION) || RUBY_PLATFORM == 'java') ? nil : :mri_20
|
12
|
+
].compact
|
11
13
|
gem 'pry', :platforms => [:jruby, :rbx]
|
12
14
|
end
|
13
15
|
|
data/Rakefile
CHANGED
@@ -42,7 +42,7 @@ end
|
|
42
42
|
|
43
43
|
namespace :spec do
|
44
44
|
namespace :rubies do
|
45
|
-
SUPPORTED_RUBIES = %w{ 1.
|
45
|
+
SUPPORTED_RUBIES = %w{ 1.9.2 1.9.3 2.0.0 jruby-1.7.0 }
|
46
46
|
|
47
47
|
desc "Run Rspec tests on all supported rubies"
|
48
48
|
task :all_tasks => [:install_gems, :exec]
|
@@ -56,6 +56,19 @@ namespace :spec do
|
|
56
56
|
task :exec do
|
57
57
|
sh %{ rvm #{SUPPORTED_RUBIES.join(',')} exec bundle exec rake spec }
|
58
58
|
end
|
59
|
+
|
60
|
+
SUPPORTED_RUBIES.each do |ruby|
|
61
|
+
desc "Run `bundle install` on #{ruby}"
|
62
|
+
task :"install_gems_#{ruby}" do
|
63
|
+
sh %{ rvm #{ruby} exec bundle install }
|
64
|
+
end
|
65
|
+
|
66
|
+
desc "Run `bundle exec rake` on #{ruby}"
|
67
|
+
task :"exec_#{ruby}" do
|
68
|
+
sh %{ rvm #{ruby} exec bundle exec rake spec }
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
59
72
|
end
|
60
73
|
end
|
61
74
|
|
@@ -81,3 +94,8 @@ Rake::RDocTask.new do |rdoc|
|
|
81
94
|
rdoc.rdoc_files.include('README*')
|
82
95
|
rdoc.rdoc_files.include('lib/**/*.rb')
|
83
96
|
end
|
97
|
+
|
98
|
+
task :wait do
|
99
|
+
print "Waiting for you to hit Enter"
|
100
|
+
$stdin.gets
|
101
|
+
end
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.9.
|
1
|
+
0.9.8
|
data/activefacts-api.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = "activefacts-api"
|
8
|
-
s.version = "0.9.
|
8
|
+
s.version = "0.9.8"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Clifford Heath"]
|
12
|
-
s.date = "2013-
|
12
|
+
s.date = "2013-11-13"
|
13
13
|
s.description = "\nThe ActiveFacts API is a Ruby DSL for managing constellations of elementary facts.\nEach fact is either existential (a value or an entity), characteristic (boolean) or\nbinary relational (A rel B). Relational facts are consistently co-referenced, so you\ncan traverse them efficiently in any direction. Each constellation maintains constraints\nover the fact population.\n"
|
14
14
|
s.email = "clifford.heath@gmail.com"
|
15
15
|
s.extra_rdoc_files = [
|
@@ -68,15 +68,15 @@ Gem::Specification.new do |s|
|
|
68
68
|
s.homepage = "http://github.com/cjheath/activefacts-api"
|
69
69
|
s.licenses = ["MIT"]
|
70
70
|
s.require_paths = ["lib"]
|
71
|
-
s.rubygems_version = "
|
71
|
+
s.rubygems_version = "2.0.5"
|
72
72
|
s.summary = "A fact-based data model DSL and API"
|
73
73
|
|
74
74
|
if s.respond_to? :specification_version then
|
75
|
-
s.specification_version =
|
75
|
+
s.specification_version = 4
|
76
76
|
|
77
77
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
78
78
|
s.add_runtime_dependency(%q<rbtree-pure>, [">= 0"])
|
79
|
-
s.add_development_dependency(%q<rake>, [">=
|
79
|
+
s.add_development_dependency(%q<rake>, [">= 10.1"])
|
80
80
|
s.add_development_dependency(%q<jeweler>, [">= 0"])
|
81
81
|
s.add_development_dependency(%q<rspec>, ["~> 2.6.0"])
|
82
82
|
s.add_development_dependency(%q<ruby-debug>, [">= 0"])
|
@@ -88,7 +88,7 @@ Gem::Specification.new do |s|
|
|
88
88
|
s.add_development_dependency(%q<rdoc>, [">= 2.4.2"])
|
89
89
|
else
|
90
90
|
s.add_dependency(%q<rbtree-pure>, [">= 0"])
|
91
|
-
s.add_dependency(%q<rake>, [">=
|
91
|
+
s.add_dependency(%q<rake>, [">= 10.1"])
|
92
92
|
s.add_dependency(%q<jeweler>, [">= 0"])
|
93
93
|
s.add_dependency(%q<rspec>, ["~> 2.6.0"])
|
94
94
|
s.add_dependency(%q<ruby-debug>, [">= 0"])
|
@@ -101,7 +101,7 @@ Gem::Specification.new do |s|
|
|
101
101
|
end
|
102
102
|
else
|
103
103
|
s.add_dependency(%q<rbtree-pure>, [">= 0"])
|
104
|
-
s.add_dependency(%q<rake>, [">=
|
104
|
+
s.add_dependency(%q<rake>, [">= 10.1"])
|
105
105
|
s.add_dependency(%q<jeweler>, [">= 0"])
|
106
106
|
s.add_dependency(%q<rspec>, ["~> 2.6.0"])
|
107
107
|
s.add_dependency(%q<ruby-debug>, [">= 0"])
|
@@ -139,8 +139,15 @@ module ActiveFacts
|
|
139
139
|
# This method removes the given instance from this constellation's indexes
|
140
140
|
# It must be called before the identifying roles get deleted or nullified.
|
141
141
|
def deindex_instance(instance) #:nodoc:
|
142
|
+
last_irns = nil
|
143
|
+
last_irvs = instance
|
142
144
|
([instance.class]+instance.class.supertypes_transitive).each do |klass|
|
143
|
-
|
145
|
+
if instance.is_a?(Entity) and last_irns != (n = klass.identifying_role_names)
|
146
|
+
# Build new identifying_role_values only when the identifying_role_names change:
|
147
|
+
last_irvs = instance.identifying_role_values(klass)
|
148
|
+
last_irns = n
|
149
|
+
end
|
150
|
+
instances[klass].delete(last_irvs)
|
144
151
|
end
|
145
152
|
# REVISIT: Need to nullify all the roles this object plays.
|
146
153
|
# If mandatory on the counterpart side, this may/must propagate the delete (without mutual recursion!)
|
@@ -45,7 +45,9 @@ module ActiveFacts
|
|
45
45
|
end
|
46
46
|
|
47
47
|
begin
|
48
|
+
@constellation.send(:instance_variable_set, :@suspend_duplicate_key_check, true)
|
48
49
|
send(role.setter, value)
|
50
|
+
@constellation.send(:instance_variable_set, :@suspend_duplicate_key_check, false)
|
49
51
|
# rescue NoMethodError => e
|
50
52
|
# raise settable_roles_exception(e, role_name)
|
51
53
|
end
|
@@ -99,8 +101,8 @@ module ActiveFacts
|
|
99
101
|
# When used as a hash key, the hash key of this entity instance is calculated
|
100
102
|
# by hashing the values of its identifying roles
|
101
103
|
def hash
|
102
|
-
self.class.
|
103
|
-
instance_variable_get(
|
104
|
+
self.class.identifying_roles.map{|role|
|
105
|
+
instance_variable_get(role.variable)
|
104
106
|
}.inject(0) { |h,v|
|
105
107
|
h ^= v.hash
|
106
108
|
h
|
@@ -391,6 +393,12 @@ module ActiveFacts
|
|
391
393
|
# which is a list of roles it plays. The identification scheme may be
|
392
394
|
# inherited from a superclass.
|
393
395
|
def identified_by(*args) #:nodoc:
|
396
|
+
options = (args[-1].is_a?(Hash) ? args.pop : {})
|
397
|
+
options.each do |key, value|
|
398
|
+
raise UnrecognisedOptionsException.new('EntityType', basename, key) unless respond_to?(key)
|
399
|
+
send(key, value)
|
400
|
+
end
|
401
|
+
|
394
402
|
raise MissingIdentificationException.new(self) unless args.size > 0
|
395
403
|
|
396
404
|
# Catch the case where we state the same identification as our superclass:
|
@@ -426,7 +434,7 @@ module ActiveFacts
|
|
426
434
|
|
427
435
|
def other.new_instance constellation, *args
|
428
436
|
instance = allocate
|
429
|
-
instance.instance_variable_set("@constellation", constellation)
|
437
|
+
instance.instance_variable_set(@@constellation_variable_name ||= "@constellation", constellation)
|
430
438
|
instance.send(:initialize, *args)
|
431
439
|
instance
|
432
440
|
end
|
@@ -33,7 +33,7 @@ module ActiveFacts
|
|
33
33
|
if is_single
|
34
34
|
"#{object_type} has a single identifying role '#{role}' which is has_one, but must be one_to_one"
|
35
35
|
else
|
36
|
-
|
36
|
+
"#{object_type} has an identifying role '#{role}' which is one_to_one, but must be has_one"
|
37
37
|
end
|
38
38
|
super msg
|
39
39
|
end
|
@@ -47,7 +47,7 @@ module ActiveFacts
|
|
47
47
|
|
48
48
|
class InvalidObjectType < SchemaException
|
49
49
|
def initialize vocabulary, klass, reason
|
50
|
-
|
50
|
+
super "A constellation over #{vocabulary.name} cannot index instances of #{klass} because it #{reason}"
|
51
51
|
end
|
52
52
|
end
|
53
53
|
|
@@ -59,7 +59,7 @@ module ActiveFacts
|
|
59
59
|
|
60
60
|
class UnrecognisedOptionsException < SchemaException
|
61
61
|
def initialize declaration, instance, option_names
|
62
|
-
|
62
|
+
super "Unrecognised options on declaration of #{declaration} #{instance}: #{option_names.inspect}"
|
63
63
|
end
|
64
64
|
end
|
65
65
|
|
data/lib/activefacts/api/guid.rb
CHANGED
@@ -4,7 +4,11 @@ require 'securerandom'
|
|
4
4
|
unless defined? SecureRandom.uuid
|
5
5
|
# I think this only applies to 1.8.6 (and JRuby/Rubinius in 1.8 mode) now:
|
6
6
|
def SecureRandom.uuid
|
7
|
-
hex(16).
|
7
|
+
hex(16).
|
8
|
+
sub(
|
9
|
+
@@format_pattern ||= /(........)(....)(....)(....)(............)/,
|
10
|
+
@@format_string ||= '\1-\2-\3-\4-\5'
|
11
|
+
)
|
8
12
|
end
|
9
13
|
end
|
10
14
|
|
@@ -4,8 +4,6 @@
|
|
4
4
|
#
|
5
5
|
# Copyright (c) 2009 Clifford Heath. Read the LICENSE file.
|
6
6
|
#
|
7
|
-
# Instance methods are extended into all instances, whether of value or entity types.
|
8
|
-
#
|
9
7
|
module ActiveFacts
|
10
8
|
module API
|
11
9
|
# Every Instance of a ObjectType (A Value type or an Entity type) includes the methods of this module:
|
@@ -36,6 +34,7 @@ module ActiveFacts
|
|
36
34
|
# We need to check each superclass that has a different identification pattern
|
37
35
|
def check_identification_change_legality(role, value)
|
38
36
|
return unless @constellation && role.is_identifying
|
37
|
+
return if @constellation.send(:instance_variable_get, :@suspend_duplicate_key_check)
|
39
38
|
|
40
39
|
klasses = [self.class] + self.class.supertypes_transitive
|
41
40
|
last_identity = nil
|
@@ -83,6 +82,15 @@ module ActiveFacts
|
|
83
82
|
# Now, for all roles (from this class and all supertypes), assign nil to all functional roles
|
84
83
|
# The counterpart roles get cleared automatically.
|
85
84
|
klasses = [self.class]+self.class.supertypes_transitive
|
85
|
+
|
86
|
+
irvks = {} # identifying_role_values by class
|
87
|
+
klasses.each do |klass|
|
88
|
+
if !irvks[klass] and klass.roles.detect{|_, role| role.counterpart and !role.counterpart.unique and send(role.getter) }
|
89
|
+
# We will need the identifying_role_values for this role's object_type
|
90
|
+
irvks[klass] = identifying_role_values(klass)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
86
94
|
klasses.each do |klass|
|
87
95
|
klass.roles.each do |role_name, role|
|
88
96
|
next if role.unary?
|
@@ -94,13 +102,15 @@ module ActiveFacts
|
|
94
102
|
i = send(role.getter)
|
95
103
|
next unless i
|
96
104
|
if counterpart.is_identifying && counterpart.mandatory
|
105
|
+
# We play a mandatory identifying role in i; so retract that (it'll clear our instance variable)
|
97
106
|
i.retract
|
98
107
|
else
|
99
108
|
if (counterpart.unique)
|
100
109
|
# REVISIT: This will incorrectly fail to propagate a key change for a non-mandatory role
|
101
110
|
i.send(counterpart.setter, nil, false)
|
102
111
|
else
|
103
|
-
i.send(role.counterpart.getter)
|
112
|
+
rv = i.send(role.counterpart.getter)
|
113
|
+
rv.delete_instance(self, irvks[role.object_type])
|
104
114
|
end
|
105
115
|
end
|
106
116
|
instance_variable_set(role.variable, nil)
|
@@ -126,10 +136,6 @@ module ActiveFacts
|
|
126
136
|
include ObjectType
|
127
137
|
# Add Instance class methods here
|
128
138
|
end
|
129
|
-
|
130
|
-
def self.included other #:nodoc:
|
131
|
-
other.send :extend, ClassMethods
|
132
|
-
end
|
133
139
|
end
|
134
140
|
end
|
135
141
|
end
|
@@ -56,6 +56,7 @@ module ActiveFacts
|
|
56
56
|
# arguments (where ObjectType is the object_type name you're interested in)
|
57
57
|
#
|
58
58
|
class InstanceIndex
|
59
|
+
attr_reader :sort
|
59
60
|
|
60
61
|
# Should be in module ForwardableWithArityChecking
|
61
62
|
def self.def_single_delegator(accessor, method, *expected_arities)
|
@@ -18,7 +18,7 @@ module ActiveFacts
|
|
18
18
|
|
19
19
|
# Each ObjectType maintains a list of the Roles it plays:
|
20
20
|
def roles(role_name = nil)
|
21
|
-
unless instance_variable_defined? "@roles" # Avoid "instance variable not defined" warning from ||=
|
21
|
+
unless instance_variable_defined?(@@roles_name ||= "@roles") # Avoid "instance variable not defined" warning from ||=
|
22
22
|
@roles = RoleCollection.new
|
23
23
|
end
|
24
24
|
case role_name
|
@@ -58,7 +58,8 @@ module ActiveFacts
|
|
58
58
|
# Define a unary fact type attached to this object_type; in essence, a boolean attribute.
|
59
59
|
#
|
60
60
|
# Example: maybe :is_ceo
|
61
|
-
def maybe(role_name)
|
61
|
+
def maybe(role_name, options = {})
|
62
|
+
raise UnrecognisedOptionsException.new("role", role_name, options.keys) unless options.empty?
|
62
63
|
realise_role(roles[role_name] = Role.new(self, TrueClass, role_name))
|
63
64
|
end
|
64
65
|
|
@@ -319,14 +320,16 @@ module ActiveFacts
|
|
319
320
|
impacts = analyse_impacts(role)
|
320
321
|
end
|
321
322
|
|
323
|
+
old_key = identifying_role_values(role.object_type) if old && mutual_propagation
|
324
|
+
|
322
325
|
instance_variable_set(role_var, value)
|
323
326
|
|
324
327
|
# Remove "self" from the old counterpart:
|
325
|
-
old.send(getter = role.counterpart.getter).
|
328
|
+
old.send(getter = role.counterpart.getter).delete_instance(self, old_key) if old_key
|
326
329
|
|
327
330
|
@constellation.when_admitted do
|
328
331
|
# Add "self" into the counterpart
|
329
|
-
value.send(getter ||= role.counterpart.getter).
|
332
|
+
value.send(getter ||= role.counterpart.getter).add_instance(self, identifying_role_values(role.object_type)) if value
|
330
333
|
|
331
334
|
apply_impacts(impacts) if impacts # Propagate dependent key changes
|
332
335
|
end
|
@@ -350,7 +353,6 @@ module ActiveFacts
|
|
350
353
|
# :class => the related class (Class object or Symbol). Not allowed if role_name was a class.
|
351
354
|
# :mandatory => true. There must be a related object for this object to be valid.
|
352
355
|
# :counterpart => Symbol/String. The name of the counterpart role. Will be to_s.snakecase'd and maybe augmented with "all_" and/or "_as_<role_name>"
|
353
|
-
# :reading => "forward/reverse". Forward and reverse readings. Must include MARKERS for the player names. May include adjectives. REVISIT: define MARKERS!
|
354
356
|
# LATER:
|
355
357
|
# :order => :local_role OR lambda{} (for sort_by)
|
356
358
|
# :restrict => Range or Array of Range/value or respond_to?(include?)
|
@@ -413,11 +415,6 @@ module ActiveFacts
|
|
413
415
|
|
414
416
|
related_role_name = related_role_name.to_s if related_role_name = options.delete(:counterpart)
|
415
417
|
|
416
|
-
reading = options.delete(:reading) # REVISIT: Implement verbalisation
|
417
|
-
role_value_constraint = options.delete(:restrict) # REVISIT: Implement role value constraints
|
418
|
-
|
419
|
-
additional_role_options options
|
420
|
-
|
421
418
|
raise UnrecognisedOptionsException.new("role", role_name, options.keys) unless options.empty?
|
422
419
|
|
423
420
|
# If you have a role "supervisor" and a sub-class "Supervisor", this'll bitch.
|
@@ -447,10 +444,6 @@ module ActiveFacts
|
|
447
444
|
]
|
448
445
|
end
|
449
446
|
|
450
|
-
def additional_role_options options
|
451
|
-
# This is a hook for extensions to override. Any extension options should be deleted from the options hash.
|
452
|
-
end
|
453
|
-
|
454
447
|
def when_bound(object_type, *args, &block)
|
455
448
|
case object_type
|
456
449
|
when Class
|
@@ -8,6 +8,67 @@ module ActiveFacts
|
|
8
8
|
module API
|
9
9
|
|
10
10
|
class RoleValues #:nodoc:
|
11
|
+
attr_accessor :sort
|
12
|
+
|
13
|
+
def initialize sort = false
|
14
|
+
@sort = !!(sort || ENV[@@af_sort_name ||= "ACTIVEFACTS_SORT"])
|
15
|
+
@a = @sort ? RBTree.new : []
|
16
|
+
end
|
17
|
+
|
18
|
+
def +(a)
|
19
|
+
if @sort
|
20
|
+
@a.values.+(a.is_a?(RoleValues) ? [a] : a)
|
21
|
+
else
|
22
|
+
@a.+(a.is_a?(RoleValues) ? [a] : a)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def to_a
|
27
|
+
@sort ? @a.values : @a
|
28
|
+
end
|
29
|
+
|
30
|
+
def keys
|
31
|
+
@sort ? @a.keys : @a
|
32
|
+
end
|
33
|
+
|
34
|
+
def single
|
35
|
+
size > 1 ? nil : to_a[0]
|
36
|
+
end
|
37
|
+
|
38
|
+
def form_key a
|
39
|
+
KeyArray.new(Array(a))
|
40
|
+
end
|
41
|
+
|
42
|
+
def add_instance(value, key)
|
43
|
+
if @sort
|
44
|
+
@a[form_key(key)] = value
|
45
|
+
else
|
46
|
+
@a << value
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
def delete_instance(value, key)
|
51
|
+
if @sort
|
52
|
+
deleted = @a.delete(form_key(key))
|
53
|
+
else
|
54
|
+
deleted = @a.delete(value)
|
55
|
+
end
|
56
|
+
|
57
|
+
# Test code:
|
58
|
+
unless deleted
|
59
|
+
p @a
|
60
|
+
p value
|
61
|
+
debugger
|
62
|
+
true
|
63
|
+
end
|
64
|
+
|
65
|
+
end
|
66
|
+
|
67
|
+
def verbalise
|
68
|
+
a = @sort ? @a.values : @a
|
69
|
+
"[#{a.map(&:verbalise).join(", ")}]"
|
70
|
+
end
|
71
|
+
|
11
72
|
# Paranoia. Because of changes in the implementation, I need to catch old code that calls these delegates incorrectly
|
12
73
|
def self.def_single_delegator(accessor, method, *expected_arities)
|
13
74
|
str = %{
|
@@ -15,12 +76,24 @@ module ActiveFacts
|
|
15
76
|
if #{expected_arities.size == 0 ? "block" : "!block || !#{expected_arities.inspect}.include?(block.arity)" }
|
16
77
|
raise ArgumentError.new("Arity mismatch on #{name}\##{method}, got \#{block ? block.arity : 'none'} want #{expected_arities.inspect} at \#{caller*"\n\t"})")
|
17
78
|
end
|
18
|
-
|
79
|
+
if @sort
|
80
|
+
#{accessor}.values.__send__(:#{method}, *args, &block)
|
81
|
+
else
|
82
|
+
#{accessor}.__send__(:#{method}, *args, &block)
|
83
|
+
end
|
19
84
|
end
|
20
85
|
}
|
21
86
|
eval(str)
|
22
87
|
end
|
23
88
|
|
89
|
+
def include? v
|
90
|
+
if @sort
|
91
|
+
@a.include?(form_key(v))
|
92
|
+
else
|
93
|
+
@a.include?(v)
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
24
97
|
def_single_delegator :@a, :all?, 1
|
25
98
|
def_single_delegator :@a, :empty?
|
26
99
|
def_single_delegator :@a, :include?
|
@@ -35,28 +108,6 @@ module ActiveFacts
|
|
35
108
|
def_single_delegator :@a, :each, *([1] + Array(defined?(::RSpec) ? -2 : nil))
|
36
109
|
def_single_delegator :@a, :detect, 1, *([1] + Array(defined?(::RSpec) ? -2 : nil))
|
37
110
|
def_single_delegator :@a, :map, 1, -1
|
38
|
-
|
39
|
-
def initialize
|
40
|
-
@a = []
|
41
|
-
end
|
42
|
-
|
43
|
-
def +(a)
|
44
|
-
@a.+(a.is_a?(RoleValues) ? [a] : a)
|
45
|
-
end
|
46
|
-
|
47
|
-
def single
|
48
|
-
size > 1 ? nil : @a[0]
|
49
|
-
end
|
50
|
-
|
51
|
-
def update(old, value)
|
52
|
-
@a.delete(old) if old
|
53
|
-
@a << value if value
|
54
|
-
end
|
55
|
-
|
56
|
-
def verbalise
|
57
|
-
"[#{@a.map(&:verbalise).join(", ")}]"
|
58
|
-
end
|
59
111
|
end
|
60
|
-
|
61
112
|
end
|
62
113
|
end
|
@@ -59,7 +59,7 @@ class Class
|
|
59
59
|
# Make this Class into a ObjectType and if necessary its module into a Vocabulary.
|
60
60
|
# The parameters are the names (Symbols) of the identifying roles.
|
61
61
|
def identified_by *args, &b
|
62
|
-
raise InvalidEntityException(self) if respond_to? :value_type # Don't make a ValueType into an EntityType
|
62
|
+
raise ActiveFacts::API::InvalidEntityException.new(self) if respond_to? :value_type # Don't make a ValueType into an EntityType
|
63
63
|
|
64
64
|
# The inclusion of instance methods triggers ClassMethods to be included in the class too
|
65
65
|
include ActiveFacts::API::Entity
|
@@ -40,7 +40,7 @@ module ActiveFacts
|
|
40
40
|
# REVISIT: args could be a hash, with keys :length, :scale, :unit, :allow
|
41
41
|
options = (args[-1].is_a?(Hash) ? args.pop : {})
|
42
42
|
options.each do |key, value|
|
43
|
-
raise UnrecognisedOptionsException.new('
|
43
|
+
raise UnrecognisedOptionsException.new('ValueType', basename, key) unless respond_to?(key)
|
44
44
|
send(key, value)
|
45
45
|
end
|
46
46
|
end
|
@@ -141,7 +141,7 @@ module ActiveFacts
|
|
141
141
|
class << klass
|
142
142
|
def new_instance constellation, *args
|
143
143
|
instance = allocate
|
144
|
-
instance.instance_variable_set("@constellation", constellation)
|
144
|
+
instance.instance_variable_set(@@constellation_variable_name ||= "@constellation", constellation)
|
145
145
|
instance.send(:initialize, *args)
|
146
146
|
instance
|
147
147
|
end
|
@@ -32,7 +32,7 @@ module ActiveFacts
|
|
32
32
|
__bind(camel)
|
33
33
|
c
|
34
34
|
else
|
35
|
-
if
|
35
|
+
if const_defined?(camel)
|
36
36
|
begin
|
37
37
|
const_get(camel)
|
38
38
|
rescue NameError
|
@@ -55,11 +55,12 @@ module ActiveFacts
|
|
55
55
|
|
56
56
|
def verbalise
|
57
57
|
"Vocabulary #{name}:\n\t" +
|
58
|
-
@object_type.keys.sort.map
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
58
|
+
@object_type.keys.sort.map do |object_type|
|
59
|
+
c = @object_type[object_type]
|
60
|
+
__bind(c.basename)
|
61
|
+
c.verbalise + "\n\t\t// Roles played: " + c.roles.verbalise
|
62
|
+
end.
|
63
|
+
join("\n\t")
|
63
64
|
end
|
64
65
|
|
65
66
|
def __add_object_type(klass) #:nodoc:
|
data/lib/activefacts/tracer.rb
CHANGED
@@ -79,19 +79,19 @@ describe "A Constellation instance" do
|
|
79
79
|
|
80
80
|
it "should complain when accessing a non-class as a method" do
|
81
81
|
Mod::Foo = 23
|
82
|
-
lambda { @constellation.Foo }.should raise_error
|
82
|
+
lambda { @constellation.Foo }.should raise_error(NoMethodError)
|
83
83
|
end
|
84
84
|
|
85
85
|
it "should complain when accessing a class that isn't an object type" do
|
86
86
|
class Mod::Bar; end
|
87
|
-
proc { @constellation.Bar }.should raise_error
|
88
|
-
proc { @constellation.instances[Mod::Bar] }.should raise_error
|
87
|
+
proc { @constellation.Bar }.should raise_error(NoMethodError)
|
88
|
+
proc { @constellation.instances[Mod::Bar] }.should raise_error(ActiveFacts::API::InvalidObjectType)
|
89
89
|
end
|
90
90
|
|
91
91
|
it "should deny handling an object type defined outside the current module" do
|
92
92
|
class ::Bar; end
|
93
|
-
lambda { @constellation.Bar }.should raise_error
|
94
|
-
lambda { @constellation.instances[Bar] }.should raise_error
|
93
|
+
lambda { @constellation.Bar }.should raise_error(NoMethodError)
|
94
|
+
lambda { @constellation.instances[Bar] }.should raise_error(ActiveFacts::API::InvalidObjectType)
|
95
95
|
end
|
96
96
|
|
97
97
|
it "should allow inspection" do
|
@@ -201,7 +201,7 @@ describe "A Constellation instance" do
|
|
201
201
|
it "Should raise an exception with assigning a role whose referent (object type) has not yet been defined" do
|
202
202
|
n = @constellation.Name("Fred")
|
203
203
|
# This does not raise the "settable_roles_exception". I'm no longer sure how I did this, so I can't get coverage on this code :(
|
204
|
-
proc { n.undefined_role = 'foo' }.should raise_error
|
204
|
+
proc { n.undefined_role = 'foo' }.should raise_error(NoMethodError)
|
205
205
|
end
|
206
206
|
|
207
207
|
# Maybe not complete yet
|
@@ -429,7 +429,7 @@ describe "A Constellation instance" do
|
|
429
429
|
has_one :thingummy, :class => Outside::Other
|
430
430
|
end
|
431
431
|
end
|
432
|
-
}.should raise_error
|
432
|
+
}.should raise_error(ActiveFacts::API::CrossVocabularyRoleException)
|
433
433
|
end
|
434
434
|
|
435
435
|
it "should disallow unrecognised supertypes" do
|
@@ -514,7 +514,7 @@ describe "A Constellation instance" do
|
|
514
514
|
supertypes :name
|
515
515
|
end
|
516
516
|
end
|
517
|
-
}.should raise_error
|
517
|
+
}.should raise_error(ActiveFacts::API::InvalidSupertypeException)
|
518
518
|
end
|
519
519
|
|
520
520
|
it "should error on invalid :class values" do
|
@@ -524,7 +524,7 @@ describe "A Constellation instance" do
|
|
524
524
|
has_one :Name, :class => 3
|
525
525
|
end
|
526
526
|
end
|
527
|
-
}.should raise_error
|
527
|
+
}.should raise_error(ArgumentError)
|
528
528
|
end
|
529
529
|
|
530
530
|
it "should error on misleading :class values" do
|
@@ -534,7 +534,7 @@ describe "A Constellation instance" do
|
|
534
534
|
has_one :Name, :class => Extra
|
535
535
|
end
|
536
536
|
end
|
537
|
-
}.should raise_error
|
537
|
+
}.should raise_error(NameError)
|
538
538
|
end
|
539
539
|
|
540
540
|
it "should allow assert using an object of the same type" do
|
@@ -572,6 +572,6 @@ describe "A Constellation instance" do
|
|
572
572
|
lambda {
|
573
573
|
# Disallowed because it re-assigns the auto_counter_val identification value
|
574
574
|
p.employer = [ "foo", {:auto_counter_val => :new}]
|
575
|
-
}.should raise_error
|
575
|
+
}.should raise_error(ActiveFacts::API::TypeConflictException)
|
576
576
|
end
|
577
577
|
end
|
@@ -364,7 +364,7 @@ describe "An instance of every type of ObjectType" do
|
|
364
364
|
a = c.AutoCounterVal(:new)
|
365
365
|
lambda {
|
366
366
|
b = 2 + a
|
367
|
-
}.should raise_error
|
367
|
+
}.should raise_error(TypeError)
|
368
368
|
a.assign(3)
|
369
369
|
lambda {
|
370
370
|
b = 2 + a
|
@@ -376,21 +376,21 @@ describe "An instance of every type of ObjectType" do
|
|
376
376
|
c = ActiveFacts::API::Constellation.new(Mod)
|
377
377
|
lambda {
|
378
378
|
c.TestByInt(:int_val => nil)
|
379
|
-
}.should raise_error
|
379
|
+
}.should raise_error(ActiveFacts::API::MissingMandatoryRoleValueException)
|
380
380
|
end
|
381
381
|
|
382
382
|
it "should complain when too many identifying values are provided for an entity" do
|
383
383
|
c = ActiveFacts::API::Constellation.new(Mod)
|
384
384
|
lambda {
|
385
385
|
c.TestByInt(2, 3)
|
386
|
-
}.should raise_error
|
386
|
+
}.should raise_error(ActiveFacts::API::UnexpectedIdentifyingValueException)
|
387
387
|
end
|
388
388
|
|
389
389
|
it "should complain when wrong type is used for an entity" do
|
390
390
|
c = ActiveFacts::API::Constellation.new(Mod)
|
391
391
|
lambda {
|
392
392
|
c.TestByInt("Not an Int")
|
393
|
-
}.should raise_error
|
393
|
+
}.should raise_error(ArgumentError)
|
394
394
|
end
|
395
395
|
|
396
396
|
it "should handle a non-mandatory missing identifying role" do
|
@@ -96,6 +96,35 @@ describe "Roles" do
|
|
96
96
|
}.should raise_error(ActiveFacts::API::CrossVocabularyRoleException)
|
97
97
|
end
|
98
98
|
|
99
|
+
it "should prevent usage of undefined options on a role" do
|
100
|
+
lambda {
|
101
|
+
module Mod
|
102
|
+
class Existing1 < String
|
103
|
+
value_type
|
104
|
+
has_one :name, :foo => :anything
|
105
|
+
end
|
106
|
+
end
|
107
|
+
}.should raise_error(ActiveFacts::API::UnrecognisedOptionsException)
|
108
|
+
|
109
|
+
lambda {
|
110
|
+
module Mod
|
111
|
+
class Existing1 < String
|
112
|
+
value_type
|
113
|
+
one_to_one :name, :foo => :anything
|
114
|
+
end
|
115
|
+
end
|
116
|
+
}.should raise_error(ActiveFacts::API::UnrecognisedOptionsException)
|
117
|
+
|
118
|
+
lambda {
|
119
|
+
module Mod
|
120
|
+
class Existing1 < String
|
121
|
+
value_type
|
122
|
+
maybe :is_broken, :foo => :anything
|
123
|
+
end
|
124
|
+
end
|
125
|
+
}.should raise_error(ActiveFacts::API::UnrecognisedOptionsException)
|
126
|
+
end
|
127
|
+
|
99
128
|
it "should provide value type metadata" do
|
100
129
|
Mod::Name.length.should == 40
|
101
130
|
Mod::Name.scale.should == 0
|
@@ -37,7 +37,7 @@ describe "An Entity Type" do
|
|
37
37
|
has_one :name
|
38
38
|
end
|
39
39
|
end
|
40
|
-
end.should raise_error
|
40
|
+
end.should raise_error(ActiveFacts::API::InvalidIdentificationException)
|
41
41
|
end
|
42
42
|
|
43
43
|
describe "when asserted" do
|
@@ -84,7 +84,7 @@ describe "An Entity Type" do
|
|
84
84
|
it "should fail if the new value already exists" do
|
85
85
|
proc do
|
86
86
|
@fly.name = 'Acme'
|
87
|
-
end.should raise_error
|
87
|
+
end.should raise_error(ActiveFacts::API::DuplicateIdentifyingValueException)
|
88
88
|
end
|
89
89
|
|
90
90
|
it "should not fail if the new value is self" do
|
@@ -234,7 +234,7 @@ describe "An Entity Type" do
|
|
234
234
|
one_to_one :number # Error, invalid identifier
|
235
235
|
end
|
236
236
|
end
|
237
|
-
end.should raise_error
|
237
|
+
end.should raise_error(ActiveFacts::API::InvalidIdentificationException)
|
238
238
|
end
|
239
239
|
|
240
240
|
describe "when asserted" do
|
@@ -294,7 +294,7 @@ describe "An Entity Type" do
|
|
294
294
|
|
295
295
|
it "should fail if the new value already exists" do
|
296
296
|
@c.Room(@b, 102)
|
297
|
-
lambda { @r.number = 102 }.should raise_error
|
297
|
+
lambda { @r.number = 102 }.should raise_error(ActiveFacts::API::DuplicateIdentifyingValueException)
|
298
298
|
end
|
299
299
|
|
300
300
|
describe "to a previously-nonexistent value" do
|
@@ -337,6 +337,7 @@ describe "An Entity Type" do
|
|
337
337
|
end
|
338
338
|
|
339
339
|
it "the old value's back-reference is set to nil" do
|
340
|
+
# @rn.all_room.should_not include @r
|
340
341
|
@rn.all_room.to_a.should_not include @r
|
341
342
|
end
|
342
343
|
|
@@ -30,7 +30,7 @@ describe 'identity change on subtype' do
|
|
30
30
|
end
|
31
31
|
|
32
32
|
it "should fail if the value is the same" do
|
33
|
-
lambda { @b = @constellation.EntityB(123, 'abc') }.should raise_error
|
33
|
+
lambda { @b = @constellation.EntityB(123, 'abc') }.should raise_error(ActiveFacts::API::UnexpectedIdentifyingValueException)
|
34
34
|
end
|
35
35
|
|
36
36
|
context "on a deep-subtype" do
|
@@ -60,4 +60,4 @@ describe 'identity change on subtype' do
|
|
60
60
|
@c.value_a.should == 987
|
61
61
|
end
|
62
62
|
end
|
63
|
-
end
|
63
|
+
end
|
@@ -75,12 +75,12 @@ describe "Entity Type class definitions" do
|
|
75
75
|
Mod::Person.roles.include?(:name).should be_true
|
76
76
|
end
|
77
77
|
|
78
|
-
it "should fail on a
|
78
|
+
it "should fail on a ValueType" do
|
79
79
|
lambda{
|
80
80
|
class SomeClass < String
|
81
|
-
identified_by
|
81
|
+
identified_by :foo
|
82
82
|
end
|
83
|
-
}.should raise_error
|
83
|
+
}.should raise_error(ActiveFacts::API::InvalidEntityException)
|
84
84
|
end
|
85
85
|
|
86
86
|
it "should return the identifying roles" do
|
@@ -88,15 +88,15 @@ describe "Entity Type class definitions" do
|
|
88
88
|
end
|
89
89
|
|
90
90
|
it "should prevent a role name from matching a object_type that exists unless that object_type is the counterpart" do
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
91
|
+
proc do
|
92
|
+
module Mod
|
93
|
+
class LegalEntity
|
94
|
+
end
|
95
|
+
class Bad
|
96
|
+
identified_by :name
|
97
|
+
has_one :name, :class => LegalEntity
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end.should raise_error(ActiveFacts::API::CrossVocabularyRoleException)
|
101
101
|
end
|
102
102
|
end
|
@@ -38,7 +38,7 @@ describe "Multi-part identifiers" do
|
|
38
38
|
end
|
39
39
|
|
40
40
|
it "should sort child keys in the instance index" do
|
41
|
-
pending "Key sorting is not supported
|
41
|
+
pending "Key sorting is not supported on this index" unless @c.Child.sort
|
42
42
|
@c.Child.keys.should == [[[@p.parent_id], 0], [[@p.parent_id], 1], [[@p.parent_id], 2]]
|
43
43
|
@c.Child.map{|k, c| c.position}.should == [@c0.position, @c1.position, @c2.position]
|
44
44
|
end
|
@@ -47,7 +47,7 @@ describe "AutoCounter Value Type instances" do
|
|
47
47
|
it "should allow prevent invalid role assignment" do
|
48
48
|
lambda {
|
49
49
|
@thing.thing_id = "foo"
|
50
|
-
}.should raise_error
|
50
|
+
}.should raise_error(ArgumentError)
|
51
51
|
end
|
52
52
|
|
53
53
|
it "should not allow its value to be re-assigned" do
|
@@ -57,7 +57,7 @@ describe "AutoCounter Value Type instances" do
|
|
57
57
|
lambda {
|
58
58
|
@thing.thing_id.assign(4)
|
59
59
|
#@thing.thing_id.assign(@thing_id)
|
60
|
-
}.should raise_error
|
60
|
+
}.should raise_error(ArgumentError)
|
61
61
|
end
|
62
62
|
|
63
63
|
it "should allow an existing counter to be re-used" do
|
@@ -72,7 +72,7 @@ describe "AutoCounter Value Type instances" do
|
|
72
72
|
it "should not allow a counter to be cloned" do
|
73
73
|
lambda {
|
74
74
|
@thing_id.clone
|
75
|
-
}.should raise_error
|
75
|
+
}.should raise_error(RuntimeError)
|
76
76
|
end
|
77
77
|
|
78
78
|
it "should allow an existing counter-identified object to be re-used" do
|
@@ -47,7 +47,7 @@ describe "Guid Value Type instances" do
|
|
47
47
|
it "should allow prevent invalid role assignment" do
|
48
48
|
lambda {
|
49
49
|
@thing.thing_id = "foo"
|
50
|
-
}.should raise_error
|
50
|
+
}.should raise_error(ArgumentError)
|
51
51
|
end
|
52
52
|
|
53
53
|
it "should allow an existing guid to be re-used" do
|
metadata
CHANGED
@@ -1,68 +1,60 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: activefacts-api
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.9.
|
5
|
-
prerelease:
|
4
|
+
version: 0.9.8
|
6
5
|
platform: ruby
|
7
6
|
authors:
|
8
7
|
- Clifford Heath
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
date: 2013-
|
11
|
+
date: 2013-11-13 00:00:00.000000000 Z
|
13
12
|
dependencies:
|
14
13
|
- !ruby/object:Gem::Dependency
|
15
14
|
name: rbtree-pure
|
16
15
|
requirement: !ruby/object:Gem::Requirement
|
17
|
-
none: false
|
18
16
|
requirements:
|
19
|
-
- -
|
17
|
+
- - '>='
|
20
18
|
- !ruby/object:Gem::Version
|
21
19
|
version: '0'
|
22
20
|
type: :runtime
|
23
21
|
prerelease: false
|
24
22
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
-
none: false
|
26
23
|
requirements:
|
27
|
-
- -
|
24
|
+
- - '>='
|
28
25
|
- !ruby/object:Gem::Version
|
29
26
|
version: '0'
|
30
27
|
- !ruby/object:Gem::Dependency
|
31
28
|
name: rake
|
32
29
|
requirement: !ruby/object:Gem::Requirement
|
33
|
-
none: false
|
34
30
|
requirements:
|
35
|
-
- -
|
31
|
+
- - '>='
|
36
32
|
- !ruby/object:Gem::Version
|
37
|
-
version: '
|
33
|
+
version: '10.1'
|
38
34
|
type: :development
|
39
35
|
prerelease: false
|
40
36
|
version_requirements: !ruby/object:Gem::Requirement
|
41
|
-
none: false
|
42
37
|
requirements:
|
43
|
-
- -
|
38
|
+
- - '>='
|
44
39
|
- !ruby/object:Gem::Version
|
45
|
-
version: '
|
40
|
+
version: '10.1'
|
46
41
|
- !ruby/object:Gem::Dependency
|
47
42
|
name: jeweler
|
48
43
|
requirement: !ruby/object:Gem::Requirement
|
49
|
-
none: false
|
50
44
|
requirements:
|
51
|
-
- -
|
45
|
+
- - '>='
|
52
46
|
- !ruby/object:Gem::Version
|
53
47
|
version: '0'
|
54
48
|
type: :development
|
55
49
|
prerelease: false
|
56
50
|
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
none: false
|
58
51
|
requirements:
|
59
|
-
- -
|
52
|
+
- - '>='
|
60
53
|
- !ruby/object:Gem::Version
|
61
54
|
version: '0'
|
62
55
|
- !ruby/object:Gem::Dependency
|
63
56
|
name: rspec
|
64
57
|
requirement: !ruby/object:Gem::Requirement
|
65
|
-
none: false
|
66
58
|
requirements:
|
67
59
|
- - ~>
|
68
60
|
- !ruby/object:Gem::Version
|
@@ -70,7 +62,6 @@ dependencies:
|
|
70
62
|
type: :development
|
71
63
|
prerelease: false
|
72
64
|
version_requirements: !ruby/object:Gem::Requirement
|
73
|
-
none: false
|
74
65
|
requirements:
|
75
66
|
- - ~>
|
76
67
|
- !ruby/object:Gem::Version
|
@@ -78,55 +69,48 @@ dependencies:
|
|
78
69
|
- !ruby/object:Gem::Dependency
|
79
70
|
name: ruby-debug
|
80
71
|
requirement: !ruby/object:Gem::Requirement
|
81
|
-
none: false
|
82
72
|
requirements:
|
83
|
-
- -
|
73
|
+
- - '>='
|
84
74
|
- !ruby/object:Gem::Version
|
85
75
|
version: '0'
|
86
76
|
type: :development
|
87
77
|
prerelease: false
|
88
78
|
version_requirements: !ruby/object:Gem::Requirement
|
89
|
-
none: false
|
90
79
|
requirements:
|
91
|
-
- -
|
80
|
+
- - '>='
|
92
81
|
- !ruby/object:Gem::Version
|
93
82
|
version: '0'
|
94
83
|
- !ruby/object:Gem::Dependency
|
95
84
|
name: debugger
|
96
85
|
requirement: !ruby/object:Gem::Requirement
|
97
|
-
none: false
|
98
86
|
requirements:
|
99
|
-
- -
|
87
|
+
- - '>='
|
100
88
|
- !ruby/object:Gem::Version
|
101
89
|
version: '0'
|
102
90
|
type: :development
|
103
91
|
prerelease: false
|
104
92
|
version_requirements: !ruby/object:Gem::Requirement
|
105
|
-
none: false
|
106
93
|
requirements:
|
107
|
-
- -
|
94
|
+
- - '>='
|
108
95
|
- !ruby/object:Gem::Version
|
109
96
|
version: '0'
|
110
97
|
- !ruby/object:Gem::Dependency
|
111
98
|
name: pry
|
112
99
|
requirement: !ruby/object:Gem::Requirement
|
113
|
-
none: false
|
114
100
|
requirements:
|
115
|
-
- -
|
101
|
+
- - '>='
|
116
102
|
- !ruby/object:Gem::Version
|
117
103
|
version: '0'
|
118
104
|
type: :development
|
119
105
|
prerelease: false
|
120
106
|
version_requirements: !ruby/object:Gem::Requirement
|
121
|
-
none: false
|
122
107
|
requirements:
|
123
|
-
- -
|
108
|
+
- - '>='
|
124
109
|
- !ruby/object:Gem::Version
|
125
110
|
version: '0'
|
126
111
|
- !ruby/object:Gem::Dependency
|
127
112
|
name: rspec
|
128
113
|
requirement: !ruby/object:Gem::Requirement
|
129
|
-
none: false
|
130
114
|
requirements:
|
131
115
|
- - ~>
|
132
116
|
- !ruby/object:Gem::Version
|
@@ -134,7 +118,6 @@ dependencies:
|
|
134
118
|
type: :development
|
135
119
|
prerelease: false
|
136
120
|
version_requirements: !ruby/object:Gem::Requirement
|
137
|
-
none: false
|
138
121
|
requirements:
|
139
122
|
- - ~>
|
140
123
|
- !ruby/object:Gem::Version
|
@@ -142,7 +125,6 @@ dependencies:
|
|
142
125
|
- !ruby/object:Gem::Dependency
|
143
126
|
name: bundler
|
144
127
|
requirement: !ruby/object:Gem::Requirement
|
145
|
-
none: false
|
146
128
|
requirements:
|
147
129
|
- - ~>
|
148
130
|
- !ruby/object:Gem::Version
|
@@ -150,7 +132,6 @@ dependencies:
|
|
150
132
|
type: :development
|
151
133
|
prerelease: false
|
152
134
|
version_requirements: !ruby/object:Gem::Requirement
|
153
|
-
none: false
|
154
135
|
requirements:
|
155
136
|
- - ~>
|
156
137
|
- !ruby/object:Gem::Version
|
@@ -158,7 +139,6 @@ dependencies:
|
|
158
139
|
- !ruby/object:Gem::Dependency
|
159
140
|
name: jeweler
|
160
141
|
requirement: !ruby/object:Gem::Requirement
|
161
|
-
none: false
|
162
142
|
requirements:
|
163
143
|
- - ~>
|
164
144
|
- !ruby/object:Gem::Version
|
@@ -166,7 +146,6 @@ dependencies:
|
|
166
146
|
type: :development
|
167
147
|
prerelease: false
|
168
148
|
version_requirements: !ruby/object:Gem::Requirement
|
169
|
-
none: false
|
170
149
|
requirements:
|
171
150
|
- - ~>
|
172
151
|
- !ruby/object:Gem::Version
|
@@ -174,34 +153,24 @@ dependencies:
|
|
174
153
|
- !ruby/object:Gem::Dependency
|
175
154
|
name: rdoc
|
176
155
|
requirement: !ruby/object:Gem::Requirement
|
177
|
-
none: false
|
178
156
|
requirements:
|
179
|
-
- -
|
157
|
+
- - '>='
|
180
158
|
- !ruby/object:Gem::Version
|
181
159
|
version: 2.4.2
|
182
160
|
type: :development
|
183
161
|
prerelease: false
|
184
162
|
version_requirements: !ruby/object:Gem::Requirement
|
185
|
-
none: false
|
186
163
|
requirements:
|
187
|
-
- -
|
164
|
+
- - '>='
|
188
165
|
- !ruby/object:Gem::Version
|
189
166
|
version: 2.4.2
|
190
|
-
description:
|
167
|
+
description: |2
|
191
168
|
|
192
169
|
The ActiveFacts API is a Ruby DSL for managing constellations of elementary facts.
|
193
|
-
|
194
|
-
|
195
|
-
or
|
196
|
-
|
197
|
-
binary relational (A rel B). Relational facts are consistently co-referenced, so
|
198
|
-
you
|
199
|
-
|
170
|
+
Each fact is either existential (a value or an entity), characteristic (boolean) or
|
171
|
+
binary relational (A rel B). Relational facts are consistently co-referenced, so you
|
200
172
|
can traverse them efficiently in any direction. Each constellation maintains constraints
|
201
|
-
|
202
173
|
over the fact population.
|
203
|
-
|
204
|
-
'
|
205
174
|
email: clifford.heath@gmail.com
|
206
175
|
executables: []
|
207
176
|
extensions: []
|
@@ -260,29 +229,25 @@ files:
|
|
260
229
|
homepage: http://github.com/cjheath/activefacts-api
|
261
230
|
licenses:
|
262
231
|
- MIT
|
232
|
+
metadata: {}
|
263
233
|
post_install_message:
|
264
234
|
rdoc_options: []
|
265
235
|
require_paths:
|
266
236
|
- lib
|
267
237
|
required_ruby_version: !ruby/object:Gem::Requirement
|
268
|
-
none: false
|
269
238
|
requirements:
|
270
|
-
- -
|
239
|
+
- - '>='
|
271
240
|
- !ruby/object:Gem::Version
|
272
241
|
version: '0'
|
273
|
-
segments:
|
274
|
-
- 0
|
275
|
-
hash: -1550200325745257681
|
276
242
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
277
|
-
none: false
|
278
243
|
requirements:
|
279
|
-
- -
|
244
|
+
- - '>='
|
280
245
|
- !ruby/object:Gem::Version
|
281
246
|
version: '0'
|
282
247
|
requirements: []
|
283
248
|
rubyforge_project:
|
284
|
-
rubygems_version:
|
249
|
+
rubygems_version: 2.0.5
|
285
250
|
signing_key:
|
286
|
-
specification_version:
|
251
|
+
specification_version: 4
|
287
252
|
summary: A fact-based data model DSL and API
|
288
253
|
test_files: []
|