active-fedora 5.5.0.rc1 → 5.5.0.rc2

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.
@@ -1,3 +1,7 @@
1
+ 5.5.0 (Unreleased)
2
+ Added support for complex rdf structures.
3
+ Changed RdfDatastream to_solr so that it uses the dsid as the solr prefix, not the datastream class name
4
+
1
5
  5.4.0
2
6
  HYDRA-850 Added finder methods like Base.where().limit().order().first
3
7
  Added Base.delete_all and Base.destroy_all
@@ -54,26 +54,26 @@ module ActiveFedora
54
54
  # queue that is kept intact down through an inheritance hierarchy.
55
55
  #
56
56
  # class Topic < ActiveFedora::Base
57
- # before_delete :destroy_author
57
+ # before_destroy :destroy_author
58
58
  # end
59
59
  #
60
60
  # class Reply < Topic
61
- # before_delete :destroy_readers
61
+ # before_destroy :destroy_readers
62
62
  # end
63
63
  #
64
- # Now, when <tt>Topic#delete</tt> is run only +destroy_author+ is called. When <tt>Reply#delete</tt> is
64
+ # Now, when <tt>Topic#destroy</tt> is run only +destroy_author+ is called. When <tt>Reply#destroy</tt> is
65
65
  # run, both +destroy_author+ and +destroy_readers+ are called. Contrast this to the following situation
66
- # where the +before_delete+ method is overridden:
66
+ # where the +before_destroy+ method is overridden:
67
67
  #
68
68
  # class Topic < ActiveFedora::Base
69
- # def before_delete() destroy_author end
69
+ # def before_destroy() destroy_author end
70
70
  # end
71
71
  #
72
72
  # class Reply < Topic
73
- # def before_delete() destroy_readers end
73
+ # def before_destroy() destroy_readers end
74
74
  # end
75
75
  #
76
- # In that case, <tt>Reply#delete</tt> would only run +destroy_readers+ and _not_ +destroy_author+.
76
+ # In that case, <tt>Reply#destroy</tt> would only run +destroy_readers+ and _not_ +destroy_author+.
77
77
  # So, use the callback macros when you want to ensure that a certain callback is called for the entire
78
78
  # hierarchy, and use the regular overwriteable methods when you want to leave it up to each descendant
79
79
  # to decide whether they want to call +super+ and trigger the inherited callbacks.
@@ -29,11 +29,6 @@ module ActiveFedora
29
29
  Deprecation.warn(RDFDatastream, "register_vocabularies no longer has any effect and will be removed in active-fedora 6.0", caller)
30
30
  end
31
31
 
32
- def prefix(name)
33
- name = name.to_s unless name.is_a? String
34
- pre = self.to_s.sub(/RDFDatastream$/i, '').underscore
35
- return "#{pre}__#{name}".to_sym
36
- end
37
32
  end
38
33
 
39
34
  attr_accessor :loaded
@@ -41,6 +36,12 @@ module ActiveFedora
41
36
  true
42
37
  end
43
38
 
39
+ def prefix(name)
40
+ name = name.to_s unless name.is_a? String
41
+ pre = dsid.underscore
42
+ return "#{pre}__#{name}".to_sym
43
+ end
44
+
44
45
  def content
45
46
  serialize
46
47
  end
@@ -67,7 +68,7 @@ module ActiveFedora
67
68
  if values
68
69
  Array(values).each do |val|
69
70
  val = val.to_s if val.kind_of? RDF::URI
70
- self.class.create_and_insert_terms(self.class.prefix(field_key), val, directive, solr_doc)
71
+ self.class.create_and_insert_terms(prefix(field_key), val, directive, solr_doc)
71
72
  end
72
73
  end
73
74
  end
@@ -1,6 +1,9 @@
1
1
  module ActiveFedora
2
2
  module RdfNode
3
3
  extend ActiveSupport::Concern
4
+ extend ActiveSupport::Autoload
5
+
6
+ autoload :TermProxy
4
7
 
5
8
  ##
6
9
  # Get the subject for this rdf object
@@ -19,7 +22,7 @@ module ActiveFedora
19
22
  # @param [Symbol, RDF::URI] predicate the predicate to insert into the graph
20
23
  def get_values(subject, predicate)
21
24
  options = config_for_term_or_uri(predicate)
22
- return TermProxy.new(self, subject, options)
25
+ TermProxy.new(self, subject, predicate, options)
23
26
  end
24
27
 
25
28
 
@@ -31,26 +34,27 @@ module ActiveFedora
31
34
  end
32
35
 
33
36
  # if there are any existing statements with this predicate, replace them
37
+ # @param [RDF::URI] subject the subject to insert into the graph
34
38
  # @param [Symbol, RDF::URI] predicate the predicate to insert into the graph
35
-
39
+ # @param [Array,#to_s] values the value/values to insert into the graph
36
40
  def set_value(subject, predicate, values)
37
-
38
- #predicate = find_predicate(predicate) unless predicate.kind_of? RDF::URI
41
+
39
42
  options = config_for_term_or_uri(predicate)
40
43
  predicate = options[:predicate]
41
44
 
42
45
  delete_predicate(subject, predicate)
43
-
44
46
  Array(values).each do |arg|
45
- arg = arg.to_s if arg.kind_of? RDF::Literal
46
- next if arg.kind_of?(String) && arg.empty?
47
+ if arg.respond_to?(:rdf_subject) # an RdfObject
48
+ graph.insert([subject, predicate, arg.rdf_subject ])
49
+ else
50
+ arg = arg.to_s if arg.kind_of? RDF::Literal
51
+ next if arg.kind_of?(String) && arg.empty?
47
52
 
48
- # If arg is a b-node, then copy it's statements onto the parent graph
49
- arg = merge_subgraph(arg) if arg.respond_to? :graph
50
- graph.insert([subject, predicate, arg])
53
+ graph.insert([subject, predicate, arg])
54
+ end
51
55
  end
52
56
 
53
- return TermProxy.new(self, subject, options)
57
+ TermProxy.new(self, subject, predicate, options)
54
58
  end
55
59
 
56
60
 
@@ -78,7 +82,7 @@ module ActiveFedora
78
82
  def append(subject, predicate, args)
79
83
  options = config_for_term_or_uri(predicate)
80
84
  graph.insert([subject, predicate, args])
81
- TermProxy.new(self, subject, options)
85
+ TermProxy.new(self, subject, options[:predicate], options)
82
86
  end
83
87
 
84
88
  def config_for_term_or_uri(term)
@@ -108,17 +112,9 @@ module ActiveFedora
108
112
 
109
113
  def method_missing(name, *args)
110
114
  if (md = /^([^=]+)=$/.match(name.to_s)) && pred = find_predicate(md[1])
111
- set_value(rdf_subject, pred, *args)
115
+ set_value(rdf_subject, pred, *args)
112
116
  elsif pred = find_predicate(name)
113
- klass = target_class(pred)
114
- if klass
115
- # return an array of klass.new from each of the values
116
- query(rdf_subject, pred).map do |solution|
117
- klass.new(graph, solution.value)
118
- end
119
- else
120
117
  get_values(rdf_subject, pred)
121
- end
122
118
  else
123
119
  super
124
120
  end
@@ -127,15 +123,6 @@ module ActiveFedora
127
123
  end
128
124
 
129
125
  private
130
- # If arg is a b-node, then copy it's statements onto the parent graph
131
- def merge_subgraph(rdf_object)
132
- rdf_object.graph.statements.each do |s|
133
- graph.insert(s)
134
- end
135
- # Return the arg to point at the new b-node
136
- rdf_object.rdf_subject
137
- end
138
-
139
126
  class Builder
140
127
  def initialize(parent)
141
128
  @parent = parent
@@ -189,55 +176,6 @@ module ActiveFedora
189
176
  end
190
177
  end
191
178
 
192
- class TermProxy
193
-
194
- attr_reader :graph, :subject, :predicate, :options
195
- delegate :class, :to_s, :==, :kind_of?, :each, :map, :empty?, :as_json, :is_a?, :to => :values
196
-
197
- def initialize(graph, subject, options)
198
- @graph = graph
199
-
200
- @subject = subject
201
- @predicate = options[:predicate]
202
- @options = options
203
- end
204
-
205
- def <<(*values)
206
- values.each { |value| graph.append(subject, predicate, value) }
207
- values
208
- end
209
-
210
- def delete(*values)
211
- values.each do |value|
212
- graph.delete_predicate(subject, predicate, value)
213
- end
214
-
215
- values
216
- end
217
-
218
- def values
219
- values = []
220
-
221
- graph.query(subject, predicate).each do |solution|
222
- v = solution.value
223
- v = v.to_s if v.is_a? RDF::Literal
224
- if options[:type] == :date
225
- v = Date.parse(v)
226
- end
227
- values << v
228
- end
229
-
230
- values
231
- end
232
-
233
- def method_missing(method, *args, &block)
234
- if values.respond_to? method
235
- values.send(method, *args, &block)
236
- else
237
- super
238
- end
239
- end
240
- end
241
179
  module ClassMethods
242
180
  def config
243
181
  @config ||= {}
@@ -0,0 +1,64 @@
1
+ module ActiveFedora
2
+ module RdfNode
3
+ class TermProxy
4
+
5
+ attr_reader :graph, :subject, :predicate, :options
6
+ delegate :class, :to_s, :==, :kind_of?, :each, :map, :empty?, :as_json, :is_a?, :to => :values
7
+
8
+ # @param graph RDF::Graph
9
+ # @param subject RDF::URI
10
+ # @param options Hash
11
+ def initialize(graph, subject, predicate, options)
12
+ @graph = graph
13
+ @subject = subject
14
+ @predicate = predicate
15
+ @options = options
16
+ end
17
+
18
+ def build
19
+ new_subject = RDF::Node.new
20
+ graph.graph.insert([subject, predicate, new_subject])
21
+ graph.target_class(predicate).new(graph.graph, new_subject)
22
+ end
23
+
24
+ def <<(*values)
25
+ values.each { |value| graph.append(subject, predicate, value) }
26
+ values
27
+ end
28
+
29
+ def delete(*values)
30
+ values.each do |value|
31
+ graph.delete_predicate(subject, predicate, value)
32
+ end
33
+
34
+ values
35
+ end
36
+
37
+ def values
38
+ values = []
39
+
40
+ graph.query(subject, predicate).each do |solution|
41
+ v = solution.value
42
+ v = v.to_s if v.is_a? RDF::Literal
43
+ if options[:type] == :date
44
+ v = Date.parse(v)
45
+ end
46
+ values << v
47
+ end
48
+ if options[:class_name]
49
+ values = values.map{ |found_subject| graph.target_class(predicate).new(graph.graph, found_subject)}
50
+ end
51
+
52
+ values
53
+ end
54
+
55
+ def method_missing(method, *args, &block)
56
+ if values.respond_to? method
57
+ values.send(method, *args, &block)
58
+ else
59
+ super
60
+ end
61
+ end
62
+ end
63
+ end
64
+ end
@@ -4,17 +4,20 @@ module ActiveFedora
4
4
 
5
5
  included do
6
6
  include RdfNode
7
+ attr_reader :rdf_subject, :graph
7
8
  end
8
9
 
9
10
  def graph
10
11
  @graph ||= RDF::Graph.new
11
- insert_type_assertion
12
12
  @graph
13
13
  end
14
14
 
15
- def initialize(graph=RDF::Graph.new, subject=nil)
15
+
16
+ def initialize(graph, subject=nil)
17
+ subject ||= RDF::Node.new
16
18
  @graph = graph
17
- @subject = subject
19
+ @rdf_subject = subject
20
+ insert_type_assertion
18
21
  end
19
22
 
20
23
  def get_values(subject, predicate)
@@ -26,7 +29,7 @@ module ActiveFedora
26
29
 
27
30
  def insert_type_assertion
28
31
  rdf_type = self.class.rdf_type
29
- @graph.insert([@subject, RDF.type, rdf_type]) if rdf_type
32
+ @graph.insert([@rdf_subject, RDF.type, rdf_type]) if rdf_type
30
33
  end
31
34
  end
32
35
  end
@@ -1,3 +1,3 @@
1
1
  module ActiveFedora
2
- VERSION = "5.5.0.rc1"
2
+ VERSION = "5.5.0.rc2"
3
3
  end
@@ -29,15 +29,15 @@ describe "Nested Rdf Objects" do
29
29
 
30
30
 
31
31
  it "should be able to nest a complex object" do
32
- comp = SpecDatastream::Component.new
32
+ comp = SpecDatastream::Component.new(ds.graph)
33
33
  comp.label = ["Alternator"]
34
34
  ds.parts = comp
35
35
  ds.parts.first.label.should == ["Alternator"]
36
36
  end
37
37
  it "should be able to nest many complex objects" do
38
- comp1 = SpecDatastream::Component.new
38
+ comp1 = SpecDatastream::Component.new ds.graph
39
39
  comp1.label = ["Alternator"]
40
- comp2 = SpecDatastream::Component.new
40
+ comp2 = SpecDatastream::Component.new ds.graph
41
41
  comp2.label = ["Crankshaft"]
42
42
  ds.parts = [comp1, comp2]
43
43
  ds.parts.first.label.should == ["Alternator"]
@@ -45,9 +45,9 @@ describe "Nested Rdf Objects" do
45
45
  end
46
46
 
47
47
  it "should be able to clear complex objects" do
48
- comp1 = SpecDatastream::Component.new
48
+ comp1 = SpecDatastream::Component.new ds.graph
49
49
  comp1.label = ["Alternator"]
50
- comp2 = SpecDatastream::Component.new
50
+ comp2 = SpecDatastream::Component.new ds.graph
51
51
  comp2.label = ["Crankshaft"]
52
52
  ds.parts = [comp1, comp2]
53
53
  ds.parts = []
@@ -63,6 +63,21 @@ _:g70350851833380 <http://purl.org/dc/terms/title> "Crankshaft" .
63
63
  END
64
64
  ds.parts.first.label.should == ["Alternator"]
65
65
  end
66
+
67
+ it "should build complex objects when a parent node doesn't exist" do
68
+ part = ds.parts.build
69
+ part.should be_kind_of SpecDatastream::Component
70
+ part.label = "Wheel bearing"
71
+ ds.parts.first.label.should == ['Wheel bearing']
72
+ end
73
+
74
+ it "should build complex objects when a parent node exists" do
75
+ ds.parts #this creates a parts node, but it shouldn't
76
+ part = ds.parts.build
77
+ part.should be_kind_of SpecDatastream::Component
78
+ part.label = "Wheel bearing"
79
+ ds.parts.first.label.should == ['Wheel bearing']
80
+ end
66
81
  end
67
82
 
68
83
  describe "with type" do
@@ -94,7 +109,7 @@ END
94
109
 
95
110
 
96
111
  it "should store the type of complex objects when type is specified" do
97
- comp = SpecDatastream::MediatorUser.new
112
+ comp = SpecDatastream::MediatorUser.new ds.graph
98
113
  comp.title = ["Doctor"]
99
114
  ds.mediator = comp
100
115
  ds.mediator.first.type.first.should be_instance_of RDF::URI
@@ -68,15 +68,15 @@ describe ActiveFedora::NtriplesRDFDatastream do
68
68
  subject.date_uploaded = Date.parse('2012-11-02')
69
69
  subject.date_uploaded.first.should be_kind_of Date
70
70
  solr_document = subject.to_solr
71
- solr_document["my_datastream__date_uploaded_dt"].should == ['2012-11-02T00:00:00Z']
71
+ solr_document["rdf__date_uploaded_dt"].should == ['2012-11-02T00:00:00Z']
72
72
  end
73
73
 
74
74
  it "should produce a solr document" do
75
75
  @subject = RdfTest.new(title: "War and Peace")
76
76
  solr_document = @subject.to_solr
77
- solr_document["my_datastream__title_display"].should == ["War and Peace"]
78
- solr_document["my_datastream__title_facet"].should == ["War and Peace"]
79
- solr_document["my_datastream__title_t"].should == ["War and Peace"]
77
+ solr_document["rdf__title_display"].should == ["War and Peace"]
78
+ solr_document["rdf__title_facet"].should == ["War and Peace"]
79
+ solr_document["rdf__title_t"].should == ["War and Peace"]
80
80
  end
81
81
 
82
82
  it "should set and recall values" do
@@ -67,16 +67,12 @@ describe ActiveFedora::NtriplesRDFDatastream do
67
67
 
68
68
  describe "some dummy instances" do
69
69
  before do
70
- class MyFoobarRDFDatastream < ActiveFedora::NtriplesRDFDatastream
71
- end
72
- class MyFoobarRdfDatastream < ActiveFedora::NtriplesRDFDatastream
73
- end
70
+ @one = ActiveFedora::RDFDatastream.new('fakepid', 'myFoobar')
71
+ @two = ActiveFedora::RDFDatastream.new('fakepid', 'myQuix')
74
72
  end
75
73
  it "should generate predictable prexies" do
76
- MyFoobarRDFDatastream.prefix("baz").should == :my_foobar__baz
77
- end
78
- it "should generate prefixes case-insensitively" do
79
- MyFoobarRDFDatastream.prefix("quux").should == MyFoobarRdfDatastream.prefix("quux")
74
+ @one .prefix("baz").should == :my_foobar__baz
75
+ @two.prefix("baz").should == :my_quix__baz
80
76
  end
81
77
  end
82
78
 
@@ -170,25 +166,25 @@ describe ActiveFedora::NtriplesRDFDatastream do
170
166
  end
171
167
  it "should iterate through @fields hash" do
172
168
  solr_doc = @subject.to_solr
173
- solr_doc["my_datastream__publisher_t"].should == ["publisher1"]
174
- solr_doc["my_datastream__publisher_sort"].should == ["publisher1"]
175
- solr_doc["my_datastream__publisher_display"].should == ["publisher1"]
176
- solr_doc["my_datastream__publisher_facet"].should == ["publisher1"]
177
- solr_doc["my_datastream__based_near_t"].sort.should == ["coverage1", "coverage2"]
178
- solr_doc["my_datastream__based_near_display"].sort.should == ["coverage1", "coverage2"]
179
- solr_doc["my_datastream__based_near_facet"].sort.should == ["coverage1", "coverage2"]
180
- solr_doc["my_datastream__created_sort"].should == ["2009-10-10"]
181
- solr_doc["my_datastream__created_display"].should == ["2009-10-10"]
182
- solr_doc["my_datastream__title_t"].should == ["fake-title"]
183
- solr_doc["my_datastream__title_sort"].should == ["fake-title"]
184
- solr_doc["my_datastream__title_display"].should == ["fake-title"]
185
- solr_doc["my_datastream__related_url_t"].should == ["http://example.org/"]
186
- solr_doc["my_datastream__empty_field_t"].should be_nil
169
+ solr_doc["solr_rdf__publisher_t"].should == ["publisher1"]
170
+ solr_doc["solr_rdf__publisher_sort"].should == ["publisher1"]
171
+ solr_doc["solr_rdf__publisher_display"].should == ["publisher1"]
172
+ solr_doc["solr_rdf__publisher_facet"].should == ["publisher1"]
173
+ solr_doc["solr_rdf__based_near_t"].sort.should == ["coverage1", "coverage2"]
174
+ solr_doc["solr_rdf__based_near_display"].sort.should == ["coverage1", "coverage2"]
175
+ solr_doc["solr_rdf__based_near_facet"].sort.should == ["coverage1", "coverage2"]
176
+ solr_doc["solr_rdf__created_sort"].should == ["2009-10-10"]
177
+ solr_doc["solr_rdf__created_display"].should == ["2009-10-10"]
178
+ solr_doc["solr_rdf__title_t"].should == ["fake-title"]
179
+ solr_doc["solr_rdf__title_sort"].should == ["fake-title"]
180
+ solr_doc["solr_rdf__title_display"].should == ["fake-title"]
181
+ solr_doc["solr_rdf__related_url_t"].should == ["http://example.org/"]
182
+ solr_doc["solr_rdf__empty_field_t"].should be_nil
187
183
 
188
184
  #should NOT have these
189
- solr_doc["my_datastream__narrator"].should be_nil
190
- solr_doc["my_datastream__empty_field"].should be_nil
191
- solr_doc["my_datastream__creator"].should be_nil
185
+ solr_doc["solr_rdf__narrator"].should be_nil
186
+ solr_doc["solr_rdf__empty_field"].should be_nil
187
+ solr_doc["solr_rdf__creator"].should be_nil
192
188
  end
193
189
 
194
190
  describe "with an actual object" do
@@ -233,16 +229,16 @@ describe ActiveFedora::NtriplesRDFDatastream do
233
229
  describe ".to_solr()" do
234
230
  it "should return the right fields" do
235
231
  @obj.to_solr.keys.count.should == 13
236
- @obj.to_solr.keys.should include("my_datastream__related_url_t", "my_datastream__publisher_t", "my_datastream__publisher_sort",
237
- "my_datastream__publisher_display", "my_datastream__publisher_facet", "my_datastream__created_sort",
238
- "my_datastream__created_display", "my_datastream__title_t", "my_datastream__title_sort", "my_datastream__title_display",
239
- "my_datastream__based_near_t", "my_datastream__based_near_facet", "my_datastream__based_near_display")
232
+ @obj.to_solr.keys.should include("solr_rdf__related_url_t", "solr_rdf__publisher_t", "solr_rdf__publisher_sort",
233
+ "solr_rdf__publisher_display", "solr_rdf__publisher_facet", "solr_rdf__created_sort",
234
+ "solr_rdf__created_display", "solr_rdf__title_t", "solr_rdf__title_sort", "solr_rdf__title_display",
235
+ "solr_rdf__based_near_t", "solr_rdf__based_near_facet", "solr_rdf__based_near_display")
240
236
 
241
237
  end
242
238
 
243
239
  it "should return the right values" do
244
- @obj.to_solr["my_datastream__related_url_t"].should == ["http://example.org/blogtastic/"]
245
- @obj.to_solr["my_datastream__based_near_t"].should == ["Tacoma, WA","Renton, WA"]
240
+ @obj.to_solr["solr_rdf__related_url_t"].should == ["http://example.org/blogtastic/"]
241
+ @obj.to_solr["solr_rdf__based_near_t"].should == ["Tacoma, WA","Renton, WA"]
246
242
  end
247
243
  end
248
244
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: active-fedora
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.5.0.rc1
4
+ version: 5.5.0.rc2
5
5
  prerelease: 6
6
6
  platform: ruby
7
7
  authors:
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2013-01-15 00:00:00.000000000 Z
14
+ date: 2013-01-17 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: rsolr
@@ -369,6 +369,7 @@ files:
369
369
  - lib/active_fedora/railtie.rb
370
370
  - lib/active_fedora/rdf_datastream.rb
371
371
  - lib/active_fedora/rdf_node.rb
372
+ - lib/active_fedora/rdf_node/term_proxy.rb
372
373
  - lib/active_fedora/rdf_object.rb
373
374
  - lib/active_fedora/rdf_xml_writer.rb
374
375
  - lib/active_fedora/rdfxml_rdf_datastream.rb