Module: ActiveFedora::DatastreamCollections

Extended by:
ActiveSupport::Concern
Defined in:
lib/active_fedora/datastream_collections.rb

Defined Under Namespace

Modules: ClassMethods

Instance Method Summary collapse

Instance Method Details

#add_named_datastream(name, opts = {}) ⇒ Object

This object is used by [datastream_name]_append helper to add a named datastream but can also be called directly.

Parameters

name: name of datastream to add
opts: hash defining datastream attributes

The following are expected keys in opts hash:

:label => Defaults to the file name
:blob or :file  => Required to point to the datastream file being added if managed content
:controlGroup => defaults to 'M' for managed, can also be 'E' external and 'R' for redirected
:content_type => required if the file does not respond to 'content_type' and should match :mimeType in has_datastream definition if defined
:dsLocation => holds uri location of datastream.  Required only if :controlGroup is type 'E' or 'R'.
:dsid or :dsId => Optional, and used to update an existing datastream with dsid supplied.  Will throw an error if dsid does not exist and does not match prefix pattern for datastream name


169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
# File 'lib/active_fedora/datastream_collections.rb', line 169

def add_named_datastream(name,opts={})
  unless named_datastreams_desc.has_key?(name) && named_datastreams_desc[name].has_key?(:type) 
    raise "Failed to add datastream. Named datastream #{name} not defined for object #{pid}." 
  end

  if opts.has_key?(:mime_type)
    opts.merge!({:content_type=>opts[:mime_type]})
  elsif opts.has_key?(:mimeType)
    opts.merge!({:content_type=>opts[:mimeType]})
  end
  opts.merge!(named_datastreams_desc[name])
    
  label = opts.has_key?(:label) ? opts[:label] : ""

  #only do these steps for managed datastreams
  unless (opts.has_key?(:controlGroup)&&opts[:controlGroup]!="M")
    if opts.has_key?(:file)
      opts.merge!({:blob => opts[:file]}) 
      opts.delete(:file)
    end
    
    raise "You must define parameter blob for this managed datastream to load for #{pid}" unless opts.has_key?(:blob)
    
    #if no explicit label and is a file use original file name for label
    if !opts.has_key?(:label)&&opts[:blob].respond_to?(:original_filename)
      label = opts[:blob].original_filename
    end
    
    if opts[:blob].respond_to?(:content_type)&&!opts[:blob].content_type.nil? && !opts.has_key?(:content_type)
      opts.merge!({:content_type=>opts[:blob].content_type})
    end

    raise "The blob must respond to content_type or the hash must have :content_type or :mime_type property set" unless opts.has_key?(:content_type)
    
    #throw error for mimeType mismatch
    if named_datastreams_desc[name].has_key?(:mimeType) && !named_datastreams_desc[name][:mimeType].eql?(opts[:content_type])
      raise "Content type mismatch for add datastream #{name} to #{pid}.  Expected: #{named_datastreams_desc[name][:mimeType]}, Actual: #{opts[:content_type]}"
    end
  else 
    label = opts[:dsLocation] if (opts.has_key?(:dsLocation)) 
  end
  
  opts.merge!(:dsLabel => label)
  
  ds = create_datastream(named_datastreams_desc[name][:type], opts[:dsid], opts)
  #Must be of type datastream
  assert_kind_of 'datastream',  ds, ActiveFedora::Datastream
  #make sure dsid is nil so that it uses the prefix for mapping purposes
  #check dsid works for the prefix if it is set
  if !ds.dsid.nil? && opts.has_key?(:prefix)
    raise "dsid supplied does not conform to pattern #{opts[:prefix]}[number]" unless ds.dsid =~ /#{opts[:prefix]}[0-9]/
  end
  
  add_datastream(ds,opts)
end

#add_named_file_datastream(name, file, opts = {}) ⇒ Object

Calls add_named_datastream while assuming it will be managed content and sets :blob and :controlGroup values accordingly

Parameters

name: Datastream name
file: The file to add for this datastream
opts: Options hash.  See +add_named_datastream+ for expected keys and values


152
153
154
155
# File 'lib/active_fedora/datastream_collections.rb', line 152

def add_named_file_datastream(name, file, opts={})
  opts.merge!({:blob=>file,:controlGroup=>'M'})
  add_named_datastream(name,opts)
end

#assert_kind_of(n, o, t) ⇒ Object

Throws an assertion failure unless the object ‘o’ is kind_of? class ‘t’

Parameters

n: Name of object
o: The object to test
t: The class type to check is kind_of?


243
244
245
# File 'lib/active_fedora/datastream_collections.rb', line 243

def assert_kind_of(n,o,t)
  raise "Assertion failure: #{n}: #{o} is not of type #{t}" unless o.kind_of?(t)
end

#datastream_namesObject

Returns array of datastream names defined for this object



143
144
145
# File 'lib/active_fedora/datastream_collections.rb', line 143

def datastream_names
  named_datastreams_desc.keys
end

#is_named_datastream?(name) ⇒ Boolean

Returns true if the name is a defined named datastream

Returns:

  • (Boolean)


248
249
250
# File 'lib/active_fedora/datastream_collections.rb', line 248

def is_named_datastream?(name)
  named_datastreams_desc.has_key?(name)
end

#named_datastreamsObject

Returns hash of datastream names defined by has_datastream calls mapped to array of datastream objects that have been added

Example

For the following has_datastream entries and a datastream defined for minivan only would be

has_datastream :name=>"minivan", :prefix => "VAN", :type=>ActiveFedora::Datastream,:mimeType=>"image/jpeg", :controlGroup=>'M'
has_datastream :name=>"external_images", :prefix=>"EXTIMG", :type=>ActiveFedora::Datastream,:mimeType=>"image/jpeg", :controlGroup=>'E'

Returns

{"external_images"=>[],"thumbnails"=>{#<ActiveFedora::Datastream:0x7ffd6512daf8 ...}}


261
262
263
264
265
266
267
# File 'lib/active_fedora/datastream_collections.rb', line 261

def named_datastreams
  ds_values = {}
  self.class.class_named_datastreams_desc.keys.each do |name|
    ds_values.merge!({name=>self.send("#{name}")})
  end
  return ds_values
end

#named_datastreams_descObject

Returns the hash that stores arguments passed to has_datastream calls within an ActiveFedora::Base child class.

has_datastream :name=>"audio_file", :prefix=>"AUDIO", :type=>ActiveFedora::Datastream, :mimeType=>"audio/x-wav" 
has_datastream :name=>"external_images", :prefix=>"EXTIMG", :type=>ActiveFedora::Datastream,:mimeType=>"image/jpeg", :controlGroup=>'E'

The above examples result in the following hash

{"audio_file"=>{:prefix=>"AUDIO",:type=>ActiveFedora::Datastream, :mimeType=>"audio/x-wav", :controlGroup=>'M'},
 "external_images=>{:prefix=>"EXTIMG", :type=>ActiveFedora::Datastream,:mimeType=>"image/jpeg", :controlGroup=>'E'}}

This hash is later used when adding a named datastream such as an “audio_file” as defined above.



138
139
140
# File 'lib/active_fedora/datastream_collections.rb', line 138

def named_datastreams_desc
  self.class_named_datastreams_desc ||= {}
end

#named_datastreams_idsObject

Returns hash of datastream names mapped to an array of dsid’s for named datastream objects

Example

For the following has_datastream call, assume we have added two datastreams.

has_datastream :name=>"thumbnails",:prefix => "THUMB",:type=>ActiveFedora::Datastream, :mimeType=>"image/jpeg", :controlGroup=>'M'

It would then return

{"thumbnails=>["THUMB1", "THUMB2"]}


278
279
280
281
282
283
284
285
# File 'lib/active_fedora/datastream_collections.rb', line 278

def named_datastreams_ids
  dsids = {}
  self.class.class_named_datastreams_desc.keys.each do |name|
    dsid_array = self.send("#{name}_ids")
    dsids[name] = dsid_array
  end
  return dsids
end

#update_named_datastream(name, opts = {}) ⇒ Object

Update an existing named datastream. It has same parameters as add_named_datastream except the :dsid key is now required.

TODO

Currently requires you to update file if a managed datastream but could change to allow metadata only updates as well



231
232
233
234
235
236
# File 'lib/active_fedora/datastream_collections.rb', line 231

def update_named_datastream(name, opts={})
  #check that dsid provided matches existing datastream with that name
  raise "You must define parameter dsid for datastream to update for #{pid}" unless opts.include?(:dsid)
  raise "Datastream with name #{name} and dsid #{opts[:dsid]} does not exist for #{pid}" unless self.send("#{name}_ids").include?(opts[:dsid])
  add_named_datastream(name,opts)
end