Module: Serializers::MARC

Included in:
Document
Defined in:
lib/serializers/marc.rb

Overview

Convert a document to a MARC record

Class Method Summary (collapse)

Instance Method Summary (collapse)

Class Method Details

+ (Object) included(base)

Register this serializer in the Document list



9
10
11
12
13
14
15
16
17
18
19
20
21
# File 'lib/serializers/marc.rb', line 9

def self.included(base)
  base.register_serializer(:marc, 'MARC', lambda { |doc| doc.to_marc },
    'http://www.loc.gov/marc/')
  base.register_serializer(:marcxml, 'MARCXML', lambda { |doc|
        xml = doc.to_marc_xml
        ret = ''
        xml.write(ret, 2)
        ret },
    'http://www.loc.gov/standards/marcxml/')
  base.register_serializer(:json, 'MARC-in-JSON', 
    lambda { |doc| doc.to_marc_json }, 
    'http://www.oclc.org/developer/content/marc-json-draft-2010-03-11')
end

Instance Method Details

- (String) author_to_marc(a) (private)

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Convert the given author (from formatted_author_list) to MARC's format

Parameters:

  • a (Hash)

    author from formatted_author_list

Returns:

  • (String)

    author formatted as MARC expects it



184
185
186
187
188
189
190
191
# File 'lib/serializers/marc.rb', line 184

def author_to_marc(a)
  author = ''
  author << a.von + ' ' unless a.von.blank?
  author << a.last
  author << ' ' + a.suffix unless a.suffix.blank?
  author << ', ' + a.first
  author
end

- (MARC::Record) to_marc

Returns this document as a MARC::Record object

Support for individual-article MARC records is spotty at best – this is a use case for which the MARC format was not intended. To generate these records, we primarily follow the advice as presented in PROPOSAL 2003-03, “Definition of Data Elements for Article Level Descsription.” We also adhere to the prior standard of providing a “free-form” citation entry in field, 773, subfield $g (Host Item Entry, Related Parts). This should ensure a reasonable degree of compatibility.

In cases where significant parts of a document record are missing (i.e., no author, no title, no year), it is possible that the MARC generated by this method will be invalid. We're currently not going out of our way to patch up records for these edge cases.

Examples:

Write out this document as MARC-XML

writer = MARC::XMLWriter.new('marc.xml')
writer.write(doc.to_marc)
writer.close()

Returns:

  • (MARC::Record)

    document as a MARC record



45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
# File 'lib/serializers/marc.rb', line 45

def to_marc
  record = ::MARC::Record.new()

  record.append(::MARC::ControlField.new('001', shasum))
  record.append(::MARC::ControlField.new('003', "PDFSHASUM"))
  record.append(::MARC::ControlField.new('005', Time.now.strftime("%Y%m%d%H%M%S.0")))
  
  if year.blank?
    year_control = '0000'
  else
    year_control = sprintf '%04d', year
  end
  record.append(::MARC::ControlField.new('008', "110501s#{year_control}       ||||fo     ||0 0|eng d"))
  
  record.append(::MARC::DataField.new('040', ' ', ' ',
    ['a', 'RLetters'], ['b', 'eng'], ['c', 'RLetters']))

  unless doi.blank?
    record.append(::MARC::DataField.new('024', '7', ' ',
      ['2', 'doi'], ['a', doi]))
  end

  unless formatted_author_list.nil? || formatted_author_list.count == 0
    record.append(::MARC::DataField.new('100', '1', ' ',
      ::MARC::Subfield.new('a', author_to_marc(formatted_author_list[0]))))

    formatted_author_list.each do |a|
      record.append(::MARC::DataField.new('700', '1', ' ',
        ::MARC::Subfield.new('a', author_to_marc(a))))
    end
  end

  unless title.blank?
    record.append(::MARC::DataField.new('245', '1', '0',
      ['a', title + (title[-1] == '.' ? nil : '.')]))
  end

  marc_volume = ''
  marc_volume << "v. #{volume}" unless volume.blank?
  marc_volume << " " if not volume.blank? and not number.blank?
  marc_volume << "no. #{number}" unless number.blank?
  record.append(::MARC::DataField.new('490', '1', ' ',
    ::MARC::Subfield.new('a', journal),
    ::MARC::Subfield.new('v', marc_volume)))
  record.append(::MARC::DataField.new('830', ' ', '0',
    ::MARC::Subfield.new('a', journal),
    ::MARC::Subfield.new('v', marc_volume)))

  marc_free = ''
  unless volume.blank?
    marc_free << "Vol. #{volume}"
    marc_free << (number.blank? ? " " : ", ")
  end
  marc_free << "no. #{number} " unless number.blank?
  marc_free << "(#{year})" unless year.blank?
  marc_free << ", p. #{pages}" unless pages.blank?

  marc_enumeration = ''
  marc_enumeration << volume unless volume.blank?
  marc_enumeration << ":#{number}" unless number.blank?
  marc_enumeration << "<#{start_page}" unless start_page.blank?

  record.append(::MARC::DataField.new('773', '0', ' ',
    ['t', journal], ['g', marc_free], 
    ['q', marc_enumeration], ['7', 'nnas']))

  subfields = []
  subfields << ['a', volume] unless volume.blank?
  subfields << ['b', number] unless number.blank?
  subfields << ['c', start_page] unless start_page.blank?
  subfields << ['i', year] unless year.blank?
  record.append(::MARC::DataField.new('363', ' ', ' ', *subfields))

  unless year.blank?
    record.append(::MARC::DataField.new('362', '0', ' ', ['a', year + '.']))
  end

  record
end

- (String) to_marc21

Note:

No tests for this method, as it is implemented by the MARC gem.

Returns this document in MARC21 transmission format

:nocov:

Examples:

Download this document as a marc file

controller.send_data doc.to_marc21, :filename => 'export.marc', :disposition => 'attachment'

Returns:

  • (String)

    document in MARC21 transmission format



134
135
136
# File 'lib/serializers/marc.rb', line 134

def to_marc21
  to_marc.to_marc
end

- (String) to_marc_json

Note:

No tests for this method, as it is implemented by the MARC gem.

Returns this document in MARC JSON format

MARC in JSON is the newest and shiniest way to transmit MARC records.

:nocov

Examples:

Download this document as a MARC-JSON file

controller.send_data doc.to_marc_json, :filename => 'export.json', :disposition => 'attachment'

Returns:

  • (String)

    document in MARC JSON format



149
150
151
# File 'lib/serializers/marc.rb', line 149

def to_marc_json
  to_marc.to_hash.to_json
end

- (REXML::Document) to_marc_xml(include_namespace = false)

Note:

No tests for this method, as it is implemented by the MARC gem.

Returns this document as MARC-XML

This method will include the XML namespace declarations in the root element by default, making this document suitable to be saved standalone. Pass false to get a plain root element, suitable for inclusion in a MARC collection.

:nocov:

Examples:

Output the document as MARC-XML in a string

ret = ''
doc.to_marc_xml.write(ret, 2)

Parameters:

  • include_namespace (Boolean) (defaults to: false)

    if false, put no namespace in the root element

Returns:

  • (REXML::Document)

    the document as a MARC-XML document



170
171
172
173
174
175
# File 'lib/serializers/marc.rb', line 170

def to_marc_xml(include_namespace = false)
  doc = REXML::Document.new
  doc << REXML::XMLDecl.new
  doc << ::MARC::XMLWriter.encode(to_marc, :include_namespace => include_namespace)
  doc
end