active-fedora 9.4.1 → 9.4.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 855f69bd4803e18b9f69462e4661f4b1411c1997
4
- data.tar.gz: d81dd2a3c2bf2b447b2bf43215629f788ee50917
3
+ metadata.gz: 35b37e4ce4fb55f72c525f6868b769f60af55d98
4
+ data.tar.gz: 8705a17f008927df6c005fe327825c70479b1abe
5
5
  SHA512:
6
- metadata.gz: 8992f6b40ac67d48ac58126507cf5c71dc6fd6c62be916b3e62d4a40f8f0305905bef9a6cf123c891943faeb2f8b1ff7e5899bc2ada8c7cf6d9360db078ede53
7
- data.tar.gz: edfefa4d6ae6811c16bbe88267601d694077a9e9c4ca67f2ac4d3a45700a921cb18271129348e0ecb488245afe0649465c93d593eebf20263383265ea42ceb79
6
+ metadata.gz: 4a534d6c9f2710b9ec7f5802bff389f3fbe8d42152a15d9494eb1c1003acc92d66b9d6727cf2c56986b7ada339ef8e7b5871fe26dcd6fee1bd7b115aee0a58ee
7
+ data.tar.gz: 6ee26660bc33f7c8bd21f2c2618f3e0b3bc74355ae022b55bd201da6a85304509a577cd28710995442e78969251a7946ba2fdfd162b810330b5beacd398e3251
@@ -1,3 +1,18 @@
1
+ v9.4.2
2
+ 2015-09-25: Refactor nested_attribute test for easier reading [Justin Coyne]
3
+
4
+ 2015-09-25: Don't skip reject_if when _destroy is passed [Justin Coyne]
5
+
6
+ 2015-09-24: Don't use Fcrepo digest predicate from rdf-vocab [Justin Coyne]
7
+
8
+ 2015-09-24: Updating documentation of Indexing Service [Jeremy Friesen]
9
+
10
+ 2015-09-24: Moving a method to protected [Jeremy Friesen]
11
+
12
+ 2015-09-23: Add high-level comment for Indexing module. [Anna Headley]
13
+
14
+ 2015-09-18: Refactor nested_attribute_spec [Justin Coyne]
15
+
1
16
  v9.4.1
2
17
  2015-09-18: Update ldp gem to 0.4.0. [Justin Coyne]
3
18
 
@@ -17,7 +17,7 @@ module ActiveFedora::File::Attributes
17
17
  def digest
18
18
  response = metadata.ldp_source.graph.query(predicate: RDF::Vocab::PREMIS.hasMessageDigest)
19
19
  # fallback on old predicate for checksum
20
- response = metadata.ldp_source.graph.query(predicate: RDF::Vocab::Fcrepo4.digest) if response.empty?
20
+ response = metadata.ldp_source.graph.query(predicate: fallback_digest_predicate) if response.empty?
21
21
  response.map(&:object)
22
22
  end
23
23
 
@@ -43,6 +43,18 @@ module ActiveFedora::File::Attributes
43
43
 
44
44
  private
45
45
 
46
+ # Fcrepo4.digest was used by Fedora < 4.3, but it was removed
47
+ # from the 2015-07-24 version of the fedora 4 ontology
48
+ # http://fedora.info/definitions/v4/2015/07/24/repository and
49
+ # from rdf-vocab in version 0.8.5
50
+ def fallback_digest_predicate
51
+ @fallback_digest ||= if RDF::Vocab::Fcrepo4.respond_to? :digest
52
+ RDF::Vocab::Fcrepo4.digest
53
+ else
54
+ ::RDF::URI("http://fedora.info/definitions/v4/repository#digest")
55
+ end
56
+ end
57
+
46
58
  def links
47
59
  @links ||= Ldp::Response.links(ldp_source.head)
48
60
  end
@@ -18,11 +18,19 @@ module ActiveFedora
18
18
  end
19
19
 
20
20
  def status
21
- fixity_graph.query(predicate: ::RDF::Vocab::Fcrepo4.status).map(&:object).first.to_s
21
+ fixity_graph.query(predicate: status_predicate).map(&:object).first.to_s
22
22
  end
23
23
 
24
24
  private
25
25
 
26
+ # Fcrepo4.status was used by Fedora < 4.3, but it was removed
27
+ # from the 2015-07-24 version of the fedora 4 ontology
28
+ # http://fedora.info/definitions/v4/2015/07/24/repository and
29
+ # from rdf-vocab in version 0.8.5
30
+ def status_predicate
31
+ ::RDF::URI("http://fedora.info/definitions/v4/repository#status")
32
+ end
33
+
26
34
  def get_fixity_response_from_fedora
27
35
  uri = target + "/fcr:fixity"
28
36
  ActiveFedora.fedora.connection.get(encoded_url(uri))
@@ -1,4 +1,12 @@
1
1
  module ActiveFedora
2
+ # Mix in this module to update Solr on save.
3
+ # Assign a new indexer at the class level where this is mixed in
4
+ # (or define an #indexing_service method)
5
+ # to change the document contents sent to solr
6
+ #
7
+ # Example indexing services are:
8
+ # @see ActiveFedora::IndexingService
9
+ # @see ActiveFedora::RDF::IndexingService
2
10
  module Indexing
3
11
  extend ActiveSupport::Concern
4
12
  extend ActiveSupport::Autoload
@@ -10,7 +18,7 @@ module ActiveFedora
10
18
  # Return a Hash representation of this object where keys in the hash are appropriate Solr field names.
11
19
  # @param [Hash] solr_doc (optional) Hash to insert the fields into
12
20
  # @param [Hash] opts (optional)
13
- # If opts[:model_only] == true, the base object metadata and the RELS-EXT datastream will be omitted. This is mainly to support shelver, which calls .to_solr for each model an object subscribes to.
21
+ # If opts[:model_only] == true, the base object metadata and the RELS-EXT datastream will be omitted. This is mainly to support shelver, which calls #to_solr for each model an object subscribes to.
14
22
  def to_solr(solr_doc = Hash.new, opts={})
15
23
  indexing_service.generate_solr_document
16
24
  end
@@ -1,4 +1,9 @@
1
1
  module ActiveFedora
2
+ # Responsible for generating the solr document (via #generate_solr_document) of the
3
+ # given object.
4
+ #
5
+ # @see ActiveFedora::Indexing
6
+ # @see ActiveFedora::RDF::IndexingService
2
7
  class IndexingService
3
8
  attr_reader :object
4
9
 
@@ -14,10 +19,6 @@ module ActiveFedora
14
19
  @profile_solr_name ||= ActiveFedora::SolrQueryBuilder.solr_name("object_profile", :displayable)
15
20
  end
16
21
 
17
- def profile_service
18
- ProfileIndexingService
19
- end
20
-
21
22
  def rdf_service
22
23
  RDF::IndexingService
23
24
  end
@@ -43,6 +44,10 @@ module ActiveFedora
43
44
 
44
45
  protected
45
46
 
47
+ def profile_service
48
+ ProfileIndexingService
49
+ end
50
+
46
51
  def c_time
47
52
  c_time = object.create_date.present? ? object.create_date : DateTime.now
48
53
  c_time = DateTime.parse(c_time) unless c_time.is_a?(DateTime)
@@ -148,7 +148,9 @@ module ActiveFedora
148
148
  attributes = attributes.with_indifferent_access
149
149
 
150
150
  if attributes['id'].blank?
151
- association.build(attributes.except(*UNASSIGNABLE_KEYS)) unless call_reject_if(association_name, attributes)
151
+ unless reject_new_record?(association_name, attributes)
152
+ association.build(attributes.except(*UNASSIGNABLE_KEYS))
153
+ end
152
154
 
153
155
  elsif existing_record = existing_records.detect { |record| record.id.to_s == attributes['id'].to_s }
154
156
  association.send(:add_record_to_target_with_callbacks, existing_record) if !association.loaded? && !call_reject_if(association_name, attributes)
@@ -176,22 +178,32 @@ module ActiveFedora
176
178
  ["1", "true"].include?(hash['_destroy'].to_s)
177
179
  end
178
180
 
181
+ # Determines if a new record should be rejected by checking
182
+ # has_destroy_flag? or if a <tt>:reject_if</tt> proc exists for this
183
+ # association and evaluates to +true+.
184
+ def reject_new_record?(association_name, attributes)
185
+ has_destroy_flag?(attributes) || call_reject_if(association_name, attributes)
186
+ end
187
+
179
188
  def raise_nested_attributes_record_not_found(association_name, record_id)
180
189
  reflection = self.class.reflect_on_association(association_name)
181
190
  raise ObjectNotFoundError, "Couldn't find #{reflection.klass.name} with ID=#{record_id} for #{self.class.name} with ID=#{id}"
182
191
  end
183
192
 
193
+ # Determines if a record with the particular +attributes+ should be
194
+ # rejected by calling the reject_if Symbol or Proc (if defined).
195
+ # The reject_if option is defined by +accepts_nested_attributes_for+.
196
+ #
197
+ # Returns false if there is a +destroy_flag+ on the attributes.
184
198
  def call_reject_if(association_name, attributes)
185
- return false if has_destroy_flag?(attributes)
186
- case callback = self.nested_attributes_options[association_name][:reject_if]
199
+ opts = self.nested_attributes_options[association_name]
200
+ return false if has_destroy_flag?(attributes) && opts[:allow_destroy]
201
+ case callback = opts[:reject_if]
187
202
  when Symbol
188
203
  method(callback).arity == 0 ? send(callback) : send(callback, attributes)
189
204
  when Proc
190
205
  callback.call(attributes)
191
206
  end
192
207
  end
193
-
194
208
  end
195
209
  end
196
-
197
-
@@ -1,4 +1,9 @@
1
1
  module ActiveFedora::RDF
2
+ # Responsible for generating the solr document (via #generate_solr_document) of the
3
+ # given object.
4
+ #
5
+ # @see ActiveFedora::Indexing
6
+ # @see ActiveFedora::IndexingService
2
7
  class IndexingService
3
8
  include Solrizer::Common
4
9
  attr_reader :object
@@ -70,7 +75,7 @@ module ActiveFedora::RDF
70
75
 
71
76
  # returns the field map instance
72
77
  def fields
73
- field_map_class.new do |field_map|
78
+ field_map_class.new do |field_map|
74
79
  index_config.each { |name, index_field_config| field_map.insert(name, index_field_config, object) }
75
80
  end
76
81
  end
@@ -1,3 +1,3 @@
1
1
  module ActiveFedora
2
- VERSION = "9.4.1"
2
+ VERSION = "9.4.2"
3
3
  end
@@ -4,128 +4,169 @@ describe "NestedAttribute behavior" do
4
4
  before do
5
5
  class Bar < ActiveFedora::Base
6
6
  belongs_to :car, predicate: ActiveFedora::RDF::Fcrepo::RelsExt.hasMember
7
- has_metadata :type=>ActiveFedora::SimpleDatastream, :name=>"someData" do |m|
8
- m.field "uno", :string
9
- m.field "dos", :string
10
- end
11
- Deprecation.silence(ActiveFedora::Attributes) do
12
- has_attributes :uno, :dos, datastream: 'someData', multiple: false
13
- end
7
+ property :uno, predicate: ::RDF::URI('http://example.com/uno'), multiple: false
8
+ property :dos, predicate: ::RDF::URI('http://example.com/dos'), multiple: false
14
9
  end
15
10
 
16
11
  # base Car class, used in test for association updates and :allow_destroy flag
17
12
  class Car < ActiveFedora::Base
18
13
  has_many :bars, predicate: ActiveFedora::RDF::Fcrepo::RelsExt.hasMember
19
- accepts_nested_attributes_for :bars, :allow_destroy=>true
20
- end
21
-
22
- # class used in test for :reject_if=>:all_blank
23
- class CarAllBlank < Car
24
- accepts_nested_attributes_for :bars, :reject_if=>:all_blank
25
- end
26
-
27
- # class used in test for :reject_if with proc object
28
- class CarProc < Car
29
- accepts_nested_attributes_for :bars, :reject_if=>proc { |attributes| attributes['uno'].blank? }
30
- end
31
-
32
- # class used in test for :reject_if with method name as symbol
33
- class CarSymbol < Car
34
- accepts_nested_attributes_for :bars, :reject_if=>:uno_blank
35
-
36
- def uno_blank(attributes)
37
- attributes['uno'].blank?
38
- end
39
- end
40
-
41
- # class used in test for :limit
42
- class CarWithLimit < Car
43
- accepts_nested_attributes_for :bars, :limit => 1
14
+ accepts_nested_attributes_for :bars, allow_destroy: true
44
15
  end
45
16
  end
46
17
  after do
47
18
  Object.send(:remove_const, :Bar)
48
- Object.send(:remove_const, :CarAllBlank)
49
- Object.send(:remove_const, :CarProc)
50
- Object.send(:remove_const, :CarSymbol)
51
- Object.send(:remove_const, :CarWithLimit)
52
19
  Object.send(:remove_const, :Car)
53
20
  end
54
21
 
22
+ let(:car_class) { Car }
23
+ let(:car) { car_class.create }
24
+ let(:bar1) { Bar.create(car: car) }
25
+ let(:bar2) { Bar.create(car: car) }
26
+
27
+
55
28
  it "should have _destroy" do
56
29
  expect(Bar.new._destroy).to be_nil
57
30
  end
58
31
 
59
32
  it "should update the child objects" do
60
- @car, @bar1, @bar2 = create_car_with_bars
61
-
62
- @car.update bars_attributes: [{id: @bar1.id, uno: "bar1 uno"}, {uno: "newbar uno"}, {id: @bar2.id, _destroy: '1', uno: 'bar2 uno'}]
63
- expect(Bar.find(@bar1.id).uno).to eq 'bar1 uno'
64
- expect(Bar.where(:id => @bar2.id).first).to be_nil
65
- expect(Bar.where(:uno => "newbar uno").first).to_not be_nil
33
+ car.update bars_attributes: [{id: bar1.id, uno: "bar1 uno"}, {uno: "newbar uno"}, {id: bar2.id, _destroy: '1', uno: 'bar2 uno'}]
34
+ expect(Bar.all.map(&:uno)).to match_array ['bar1 uno', 'newbar uno']
66
35
 
67
- bars = @car.bars(true)
68
- expect(bars).to include(@bar1)
69
- expect(bars).to_not include(@bar2)
36
+ bars = car.bars(true)
37
+ expect(bars).to include(bar1)
38
+ expect(bars).to_not include(bar2)
70
39
  end
71
40
 
72
- it "should reject attributes when all blank" do
73
- @car, @bar1, @bar2 = create_car_with_bars(CarAllBlank)
41
+ context "when reject_if: :all_blank" do
42
+ before do
43
+ class CarAllBlank < Car
44
+ accepts_nested_attributes_for :bars, reject_if: :all_blank
45
+ end
46
+ end
47
+
48
+ let(:car_class) { CarAllBlank }
49
+ after { Object.send(:remove_const, :CarAllBlank) }
50
+ let(:car) { car_class.create }
51
+ let!(:bar1) { Bar.create(car: car) }
52
+ let!(:bar2) { Bar.create(car: car) }
74
53
 
75
- expect(@car.bars.count).to eq 2
76
- @car.update bars_attributes: [{}, {:id=>@bar1.id, :uno=>"bar1 uno"}]
77
- expect(@car.bars(true).count).to eq 2
54
+ it "should reject attributes when all blank" do
55
+ expect(car.bars.count).to eq 2
56
+ car.update bars_attributes: [{}, {id: bar1.id, uno: "bar1 uno"}]
57
+ expect(car.bars(true).count).to eq 2
78
58
 
79
- @bar1.reload
80
- expect(@bar1.uno).to eq "bar1 uno"
59
+ bar1.reload
60
+ expect(bar1.uno).to eq "bar1 uno"
61
+ end
81
62
  end
82
63
 
83
- it "should reject attributes based on proc" do
84
- @car, @bar1, @bar2 = create_car_with_bars(CarProc)
64
+ context "when reject_if attribute is supplied with a proc" do
65
+ before do
66
+ class CarProc < Car
67
+ accepts_nested_attributes_for :bars, reject_if: ->(attributes) { attributes['uno'].blank? }
68
+ end
69
+ end
85
70
 
86
- @car.update bars_attributes: [{}, {:id=>@bar1.id, :uno=>"bar1 uno"}, {:id=>@bar2.id, :dos=>"bar2 dos"}]
87
- @bar1.reload
88
- @bar2.reload
89
- expect(@bar1.uno).to eq "bar1 uno"
90
- expect(@bar2.dos).to be_nil
91
- end
71
+ after { Object.send(:remove_const, :CarProc) }
72
+ let(:car_class) { CarProc }
73
+
74
+ context "and the reject_if proc evaluates to false" do
75
+ before do
76
+ car.update bars_attributes: [{}, { id: bar1.id, uno: "bar1 uno" }]
77
+ end
78
+ it "updates attributes" do
79
+ expect(bar1.reload.uno).to eq "bar1 uno"
80
+ end
81
+ end
82
+
83
+ context "and the reject_if proc evaluates to true" do
84
+ before do
85
+ car.update bars_attributes: [{}, { id: bar1.id, dos: "bar1 uno" }]
86
+ end
87
+ it "rejects attributes" do
88
+ expect(bar1.reload.dos).to be_nil
89
+ end
90
+ end
92
91
 
93
- it "should reject attributes base on method name" do
94
- @car, @bar1, @bar2 = create_car_with_bars(CarSymbol)
92
+ context "and `allow_destroy: false`" do
93
+ context "and the reject_if proc evaluates to true" do
94
+ before do
95
+ car.update bars_attributes: [{}, { id: bar1.id, dos: "bar1 uno", _destroy: "1" }]
96
+ end
97
+ it "rejects attributes (_destroy doesn't affect the outcome)" do
98
+ expect(bar1.reload.dos).to be_nil
99
+ end
100
+ end
95
101
 
96
- @car.update bars_attributes: [{}, {:id=>@bar1.id, :uno=>"bar1 uno"}, {:id=>@bar2.id, :dos=>"bar2 dos"}]
97
- @bar1.reload
98
- @bar2.reload
99
- expect(@bar1.uno).to eq "bar1 uno"
100
- expect(@bar2.dos).to be_nil
102
+ context "a record with the destroy flag and without an id" do
103
+ it "creates a new record" do
104
+ expect {
105
+ car.update bars_attributes: [{ uno: "bar1 uno", _destroy: "1" }]
106
+ }.not_to change { car.bars(true).count }
107
+ end
108
+ end
109
+ end
101
110
  end
102
111
 
103
- it "should throw TooManyRecords" do
104
- @car, @bar1, @bar2 = create_car_with_bars(CarWithLimit)
112
+ describe "reject_if: with a symbol" do
113
+ before do
114
+ # class used in test for reject_if: with method name as symbol
115
+ class CarSymbol < Car
116
+ accepts_nested_attributes_for :bars, reject_if: :uno_blank
105
117
 
106
- expect {
107
- @car.attributes = {:bars_attributes=>[{}]}
108
- }.to_not raise_exception
118
+ def uno_blank(attributes)
119
+ attributes['uno'].blank?
120
+ end
121
+ end
122
+ end
109
123
 
110
- expect {
111
- @car.attributes = {:bars_attributes=>[{}, {}]}
112
- }.to raise_exception(ActiveFedora::NestedAttributes::TooManyRecords)
124
+ after { Object.send(:remove_const, :CarSymbol) }
125
+ let(:car_class) { CarSymbol }
126
+
127
+ it "rejects attributes based on method name" do
128
+ car.update bars_attributes: [{}, {id: bar1.id, uno: "bar1 uno"}, {id: bar2.id, dos: "bar2 dos"}]
129
+ bar1.reload
130
+ bar2.reload
131
+ expect(bar1.uno).to eq "bar1 uno"
132
+ expect(bar2.dos).to be_nil
133
+ end
113
134
  end
114
135
 
115
- private
136
+ describe "allow_destroy: true" do
137
+ before do
138
+ class CarDestroy < Car
139
+ accepts_nested_attributes_for :bars, allow_destroy: true
140
+ end
141
+ end
116
142
 
117
- # Helper method used to create 1 Car and 2 Bars (with option to provide classes for both models)
118
- #
119
- # @param car_class [class] class for new `car` object, default Car
120
- # @param bar_class [class] class for new `bar` object, default Bar
121
- #
122
- # @return [car,bar,bar] returns 1 Car and 2 Bars
123
- def create_car_with_bars(car_class = Car, bar_class = Bar)
124
- car = car_class.new; car.save!
143
+ let(:car_class) { CarDestroy }
144
+ after { Object.send(:remove_const, :CarDestroy) }
125
145
 
126
- bar1 = bar_class.new(car: car); bar1.save!
127
- bar2 = bar_class.new(car: car); bar2.save!
128
- [car, bar1, bar2]
146
+ it "doesn't create a new record if _destroy is set" do
147
+ expect {
148
+ car.update bars_attributes: [{ uno: "new uno", _destroy: "1" }]
149
+ }.not_to change { car.bars(true).count }
150
+ end
129
151
  end
130
152
 
153
+ describe "limit" do
154
+ before do
155
+ class CarWithLimit < Car
156
+ accepts_nested_attributes_for :bars, limit: 1
157
+ end
158
+ end
159
+ after { Object.send(:remove_const, :CarWithLimit) }
160
+
161
+ let(:car_class) { CarWithLimit }
162
+ it "should throw TooManyRecords" do
163
+ expect {
164
+ car.attributes = {bars_attributes: [{}]}
165
+ }.to_not raise_exception
166
+
167
+ expect {
168
+ car.attributes = {bars_attributes: [{}, {}]}
169
+ }.to raise_exception(ActiveFedora::NestedAttributes::TooManyRecords)
170
+ end
171
+ end
131
172
  end
@@ -232,8 +232,10 @@ describe ActiveFedora::File do
232
232
  end
233
233
  context "with pre-4.3.0 predicate" do
234
234
  before do
235
+ predicate = ::RDF::URI("http://fedora.info/definitions/v4/repository#digest")
236
+ object = RDF::URI.new("urn:sha1:f1d2d2f924e986ac86fdf7b36c94bcdf32beec15")
235
237
  graph = ActiveTriples::Resource.new
236
- graph << RDF::Statement.new(file.uri, RDF::Vocab::Fcrepo4.digest, RDF::URI.new("urn:sha1:f1d2d2f924e986ac86fdf7b36c94bcdf32beec15"))
238
+ graph << RDF::Statement.new(file.uri, predicate, object)
237
239
  allow(file).to receive_message_chain(:metadata, :ldp_source, :graph).and_return(graph)
238
240
  end
239
241
  it "falls back on fedora:digest if premis:hasMessageDigest is not present" do
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: 9.4.1
4
+ version: 9.4.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Matt Zumwalt
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2015-09-18 00:00:00.000000000 Z
13
+ date: 2015-09-25 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rsolr