cacofonix 0.10.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +2 -0
- data/.rvmrc +1 -0
- data/.travis.yml +10 -0
- data/CHANGELOG.md +205 -0
- data/CODE_OF_CONDUCT.md +74 -0
- data/Gemfile +5 -0
- data/LICENSE.txt +22 -0
- data/README.md +76 -0
- data/Rakefile +6 -0
- data/TODO +14 -0
- data/bin/onix_extract_codelists +41 -0
- data/cacofonix.gemspec +39 -0
- data/data/9780194351898.xml +74 -0
- data/data/Ashgate Other.xml +382679 -0
- data/data/Bookwise_July_2008.xml +21611 -0
- data/data/Peribo Onix 0408.xml +17051 -0
- data/data/aau.xml +96 -0
- data/data/audience_range.xml +9 -0
- data/data/contributor.xml +6 -0
- data/data/control_chars.xml +74 -0
- data/data/entities.xml +78 -0
- data/data/extra_entities.xml +65 -0
- data/data/header.xml +21 -0
- data/data/header_invalid_sentdate.xml +21 -0
- data/data/hlasep08.xml +24519 -0
- data/data/imprint.xml +5 -0
- data/data/iso_8859_1.xml +58 -0
- data/data/jul.xml +24783 -0
- data/data/language.xml +7 -0
- data/data/market_representation.xml +11 -0
- data/data/measure.xml +6 -0
- data/data/media_file.xml +6 -0
- data/data/no_encoding.xml +78 -0
- data/data/no_xml_declaration.xml +95 -0
- data/data/other_text.xml +5 -0
- data/data/price.xml +5 -0
- data/data/product.xml +79 -0
- data/data/product_identifier.xml +5 -0
- data/data/product_invalid_pubdate.xml +42 -0
- data/data/publisher.xml +5 -0
- data/data/rba_FANT.xml +23 -0
- data/data/reference_with_release_attrib.xml +74 -0
- data/data/sales_restriction.xml +4 -0
- data/data/sales_rights.xml +35 -0
- data/data/sender_identifier.xml +5 -0
- data/data/series.xml +5 -0
- data/data/series_identifier.xml +6 -0
- data/data/short_tags.xml +191 -0
- data/data/short_tags_ivp.xml +231 -0
- data/data/sl_product.xml +81 -0
- data/data/stock.xml +5 -0
- data/data/subject.xml +6 -0
- data/data/supply_detail.xml +18 -0
- data/data/title.xml +6 -0
- data/data/two_products.xml +114 -0
- data/data/usd.xml +175 -0
- data/data/utf_16.xml +0 -0
- data/data/website.xml +6 -0
- data/examples/reader.rb +25 -0
- data/examples/reader_apa.rb +22 -0
- data/examples/writer.rb +13 -0
- data/examples/writer_apa.rb +38 -0
- data/lib/cacofonix.rb +151 -0
- data/lib/cacofonix/codelists/001.rb +16 -0
- data/lib/cacofonix/codelists/002.rb +11 -0
- data/lib/cacofonix/codelists/003.rb +13 -0
- data/lib/cacofonix/codelists/005.rb +20 -0
- data/lib/cacofonix/codelists/006.rb +82 -0
- data/lib/cacofonix/codelists/007.rb +129 -0
- data/lib/cacofonix/codelists/008.rb +13 -0
- data/lib/cacofonix/codelists/009.rb +13 -0
- data/lib/cacofonix/codelists/010.rb +52 -0
- data/lib/cacofonix/codelists/011.rb +17 -0
- data/lib/cacofonix/codelists/012.rb +17 -0
- data/lib/cacofonix/codelists/013.rb +13 -0
- data/lib/cacofonix/codelists/014.rb +10 -0
- data/lib/cacofonix/codelists/015.rb +19 -0
- data/lib/cacofonix/codelists/016.rb +12 -0
- data/lib/cacofonix/codelists/017.rb +96 -0
- data/lib/cacofonix/codelists/018.rb +11 -0
- data/lib/cacofonix/codelists/019.rb +13 -0
- data/lib/cacofonix/codelists/020.rb +7 -0
- data/lib/cacofonix/codelists/021.rb +39 -0
- data/lib/cacofonix/codelists/022.rb +15 -0
- data/lib/cacofonix/codelists/023.rb +19 -0
- data/lib/cacofonix/codelists/024.rb +17 -0
- data/lib/cacofonix/codelists/025.rb +35 -0
- data/lib/cacofonix/codelists/026.rb +86 -0
- data/lib/cacofonix/codelists/027.rb +90 -0
- data/lib/cacofonix/codelists/028.rb +14 -0
- data/lib/cacofonix/codelists/029.rb +25 -0
- data/lib/cacofonix/codelists/030.rb +22 -0
- data/lib/cacofonix/codelists/031.rb +9 -0
- data/lib/cacofonix/codelists/032.rb +8 -0
- data/lib/cacofonix/codelists/033.rb +43 -0
- data/lib/cacofonix/codelists/034.rb +21 -0
- data/lib/cacofonix/codelists/035.rb +12 -0
- data/lib/cacofonix/codelists/036.rb +9 -0
- data/lib/cacofonix/codelists/037.rb +12 -0
- data/lib/cacofonix/codelists/038.rb +43 -0
- data/lib/cacofonix/codelists/039.rb +14 -0
- data/lib/cacofonix/codelists/040.rb +12 -0
- data/lib/cacofonix/codelists/041.rb +12 -0
- data/lib/cacofonix/codelists/042.rb +22 -0
- data/lib/cacofonix/codelists/043.rb +12 -0
- data/lib/cacofonix/codelists/044.rb +22 -0
- data/lib/cacofonix/codelists/045.rb +19 -0
- data/lib/cacofonix/codelists/046.rb +15 -0
- data/lib/cacofonix/codelists/047.rb +10 -0
- data/lib/cacofonix/codelists/048.rb +17 -0
- data/lib/cacofonix/codelists/049.rb +91 -0
- data/lib/cacofonix/codelists/050.rb +14 -0
- data/lib/cacofonix/codelists/051.rb +36 -0
- data/lib/cacofonix/codelists/052.rb +7 -0
- data/lib/cacofonix/codelists/053.rb +10 -0
- data/lib/cacofonix/codelists/054.rb +29 -0
- data/lib/cacofonix/codelists/055.rb +23 -0
- data/lib/cacofonix/codelists/056.rb +8 -0
- data/lib/cacofonix/codelists/057.rb +11 -0
- data/lib/cacofonix/codelists/058.rb +29 -0
- data/lib/cacofonix/codelists/059.rb +13 -0
- data/lib/cacofonix/codelists/060.rb +8 -0
- data/lib/cacofonix/codelists/061.rb +9 -0
- data/lib/cacofonix/codelists/062.rb +11 -0
- data/lib/cacofonix/codelists/063.rb +7 -0
- data/lib/cacofonix/codelists/064.rb +19 -0
- data/lib/cacofonix/codelists/065.rb +34 -0
- data/lib/cacofonix/codelists/066.rb +10 -0
- data/lib/cacofonix/codelists/067.rb +8 -0
- data/lib/cacofonix/codelists/068.rb +22 -0
- data/lib/cacofonix/codelists/069.rb +10 -0
- data/lib/cacofonix/codelists/070.rb +8 -0
- data/lib/cacofonix/codelists/071.rb +16 -0
- data/lib/cacofonix/codelists/072.rb +13 -0
- data/lib/cacofonix/codelists/073.rb +42 -0
- data/lib/cacofonix/codelists/074.rb +495 -0
- data/lib/cacofonix/codelists/075.rb +8 -0
- data/lib/cacofonix/codelists/076.rb +18 -0
- data/lib/cacofonix/codelists/077.rb +25 -0
- data/lib/cacofonix/codelists/078.rb +173 -0
- data/lib/cacofonix/codelists/079.rb +25 -0
- data/lib/cacofonix/codelists/080.rb +26 -0
- data/lib/cacofonix/codelists/081.rb +45 -0
- data/lib/cacofonix/codelists/082.rb +23 -0
- data/lib/cacofonix/codelists/083.rb +74 -0
- data/lib/cacofonix/codelists/084.rb +16 -0
- data/lib/cacofonix/codelists/085.rb +29 -0
- data/lib/cacofonix/codelists/086.rb +11 -0
- data/lib/cacofonix/codelists/087.rb +12 -0
- data/lib/cacofonix/codelists/088.rb +7 -0
- data/lib/cacofonix/codelists/089.rb +7 -0
- data/lib/cacofonix/codelists/090.rb +17 -0
- data/lib/cacofonix/codelists/091.rb +257 -0
- data/lib/cacofonix/codelists/092.rb +14 -0
- data/lib/cacofonix/codelists/093.rb +19 -0
- data/lib/cacofonix/codelists/094.rb +9 -0
- data/lib/cacofonix/codelists/095.rb +9 -0
- data/lib/cacofonix/codelists/096.rb +191 -0
- data/lib/cacofonix/codelists/097.rb +7 -0
- data/lib/cacofonix/codelists/098.rb +27 -0
- data/lib/cacofonix/codelists/099.rb +30 -0
- data/lib/cacofonix/codelists/100.rb +12 -0
- data/lib/cacofonix/codelists/101.rb +8 -0
- data/lib/cacofonix/codelists/102.rb +9 -0
- data/lib/cacofonix/codelists/121.rb +164 -0
- data/lib/cacofonix/codelists/138.rb +12 -0
- data/lib/cacofonix/codelists/139.rb +76 -0
- data/lib/cacofonix/codelists/140.rb +13 -0
- data/lib/cacofonix/codelists/141.rb +16 -0
- data/lib/cacofonix/codelists/142.rb +18 -0
- data/lib/cacofonix/codelists/143.rb +13 -0
- data/lib/cacofonix/codelists/144.rb +12 -0
- data/lib/cacofonix/codelists/145.rb +13 -0
- data/lib/cacofonix/codelists/146.rb +9 -0
- data/lib/cacofonix/codelists/147.rb +16 -0
- data/lib/cacofonix/codelists/148.rb +9 -0
- data/lib/cacofonix/codelists/149.rb +10 -0
- data/lib/cacofonix/codelists/150.rb +130 -0
- data/lib/cacofonix/codelists/151.rb +13 -0
- data/lib/cacofonix/codelists/152.rb +8 -0
- data/lib/cacofonix/codelists/153.rb +20 -0
- data/lib/cacofonix/codelists/154.rb +15 -0
- data/lib/cacofonix/codelists/155.rb +11 -0
- data/lib/cacofonix/codelists/156.rb +10 -0
- data/lib/cacofonix/codelists/157.rb +10 -0
- data/lib/cacofonix/codelists/158.rb +32 -0
- data/lib/cacofonix/codelists/159.rb +12 -0
- data/lib/cacofonix/codelists/160.rb +10 -0
- data/lib/cacofonix/codelists/161.rb +9 -0
- data/lib/cacofonix/codelists/162.rb +12 -0
- data/lib/cacofonix/codelists/163.rb +17 -0
- data/lib/cacofonix/codelists/164.rb +11 -0
- data/lib/cacofonix/codelists/165.rb +9 -0
- data/lib/cacofonix/codelists/166.rb +9 -0
- data/lib/cacofonix/codelists/167.rb +9 -0
- data/lib/cacofonix/codelists/168.rb +8 -0
- data/lib/cacofonix/codelists/169.rb +9 -0
- data/lib/cacofonix/codelists/170.rb +7 -0
- data/lib/cacofonix/codelists/171.rb +8 -0
- data/lib/cacofonix/codelists/172.rb +7 -0
- data/lib/cacofonix/codelists/173.rb +8 -0
- data/lib/cacofonix/codelists/174.rb +8 -0
- data/lib/cacofonix/codelists/175.rb +206 -0
- data/lib/cacofonix/codelists/176.rb +20 -0
- data/lib/cacofonix/codelists/177.rb +8 -0
- data/lib/cacofonix/codelists/178.rb +24 -0
- data/lib/cacofonix/codelists/179.rb +7 -0
- data/lib/cacofonix/codelists/184.rb +11 -0
- data/lib/cacofonix/core/code.rb +106 -0
- data/lib/cacofonix/core/element.rb +275 -0
- data/lib/cacofonix/core/header.rb +45 -0
- data/lib/cacofonix/core/lists.rb +108 -0
- data/lib/cacofonix/core/reader.rb +166 -0
- data/lib/cacofonix/core/writer.rb +123 -0
- data/lib/cacofonix/elements/addressee_identifier.rb +6 -0
- data/lib/cacofonix/elements/agent_identifier.rb +6 -0
- data/lib/cacofonix/elements/audience.rb +8 -0
- data/lib/cacofonix/elements/audience_range.rb +15 -0
- data/lib/cacofonix/elements/batch_bonus.rb +7 -0
- data/lib/cacofonix/elements/bible.rb +12 -0
- data/lib/cacofonix/elements/complexity.rb +7 -0
- data/lib/cacofonix/elements/conference.rb +14 -0
- data/lib/cacofonix/elements/conference_sponsor.rb +8 -0
- data/lib/cacofonix/elements/conference_sponsor_identifier.rb +6 -0
- data/lib/cacofonix/elements/contained_item.rb +6 -0
- data/lib/cacofonix/elements/content_item.rb +21 -0
- data/lib/cacofonix/elements/contributor.rb +19 -0
- data/lib/cacofonix/elements/copyright_owner.rb +8 -0
- data/lib/cacofonix/elements/copyright_owner_identifier.rb +6 -0
- data/lib/cacofonix/elements/copyright_statement.rb +7 -0
- data/lib/cacofonix/elements/discount_coded.rb +8 -0
- data/lib/cacofonix/elements/extent.rb +8 -0
- data/lib/cacofonix/elements/identifier.rb +7 -0
- data/lib/cacofonix/elements/illustrations.rb +8 -0
- data/lib/cacofonix/elements/imprint.rb +9 -0
- data/lib/cacofonix/elements/language.rb +8 -0
- data/lib/cacofonix/elements/location_identifier.rb +8 -0
- data/lib/cacofonix/elements/main_subject.rb +9 -0
- data/lib/cacofonix/elements/market_date.rb +8 -0
- data/lib/cacofonix/elements/market_representation.rb +18 -0
- data/lib/cacofonix/elements/measure.rb +8 -0
- data/lib/cacofonix/elements/media_file.rb +16 -0
- data/lib/cacofonix/elements/name.rb +6 -0
- data/lib/cacofonix/elements/name_base.rb +17 -0
- data/lib/cacofonix/elements/new_supplier.rb +12 -0
- data/lib/cacofonix/elements/not_for_sale.rb +13 -0
- data/lib/cacofonix/elements/on_order_detail.rb +7 -0
- data/lib/cacofonix/elements/other_text.rb +17 -0
- data/lib/cacofonix/elements/page_run.rb +7 -0
- data/lib/cacofonix/elements/person_date.rb +8 -0
- data/lib/cacofonix/elements/person_name_identifier.rb +6 -0
- data/lib/cacofonix/elements/price.rb +46 -0
- data/lib/cacofonix/elements/prize.rb +10 -0
- data/lib/cacofonix/elements/product.rb +155 -0
- data/lib/cacofonix/elements/product_base.rb +61 -0
- data/lib/cacofonix/elements/product_classification.rb +8 -0
- data/lib/cacofonix/elements/product_form_feature.rb +8 -0
- data/lib/cacofonix/elements/product_identifier.rb +6 -0
- data/lib/cacofonix/elements/professional_affiliation.rb +7 -0
- data/lib/cacofonix/elements/publisher.rb +11 -0
- data/lib/cacofonix/elements/reissue.rb +9 -0
- data/lib/cacofonix/elements/related_product.rb +6 -0
- data/lib/cacofonix/elements/religious_text.rb +8 -0
- data/lib/cacofonix/elements/religious_text_feature.rb +8 -0
- data/lib/cacofonix/elements/sales_outlet.rb +7 -0
- data/lib/cacofonix/elements/sales_outlet_identifier.rb +6 -0
- data/lib/cacofonix/elements/sales_restriction.rb +7 -0
- data/lib/cacofonix/elements/sales_rights.rb +13 -0
- data/lib/cacofonix/elements/sender_identifier.rb +6 -0
- data/lib/cacofonix/elements/series.rb +11 -0
- data/lib/cacofonix/elements/series_identifier.rb +6 -0
- data/lib/cacofonix/elements/set.rb +13 -0
- data/lib/cacofonix/elements/stock.rb +16 -0
- data/lib/cacofonix/elements/stock_quantity_coded.rb +8 -0
- data/lib/cacofonix/elements/subject.rb +13 -0
- data/lib/cacofonix/elements/supplier_identifier.rb +6 -0
- data/lib/cacofonix/elements/supply_detail.rb +37 -0
- data/lib/cacofonix/elements/text_item.rb +11 -0
- data/lib/cacofonix/elements/text_item_identifier.rb +6 -0
- data/lib/cacofonix/elements/title.rb +11 -0
- data/lib/cacofonix/elements/website.rb +8 -0
- data/lib/cacofonix/elements/work_identifier.rb +6 -0
- data/lib/cacofonix/utils/code_list_extractor.rb +112 -0
- data/lib/cacofonix/utils/normaliser.rb +125 -0
- data/lib/cacofonix/version.rb +5 -0
- data/lib/cacofonix/wrappers/apa_product.rb +748 -0
- data/lib/cacofonix/wrappers/simple_product.rb +49 -0
- data/support/entities.txt +1499 -0
- data/support/extract.rb +25 -0
- data/support/switch-onix-2.1-short-to-reference.xsl +24 -0
- data/support/switch-onix-tagnames-1.1.xsl +25 -0
- data/support/switch-onix-tagnames-2.0.xsl +37 -0
- metadata +438 -0
@@ -0,0 +1,45 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
module Cacofonix
|
4
|
+
class Header
|
5
|
+
include ROXML
|
6
|
+
|
7
|
+
xml_name "Header"
|
8
|
+
|
9
|
+
xml_accessor :from_ean_number, :from => "FromEANNumber"
|
10
|
+
xml_accessor :from_san, :from => "FromSAN"
|
11
|
+
xml_accessor :sender_identifiers, :from => "SenderIdentifier", :as => [Cacofonix::SenderIdentifier]
|
12
|
+
xml_accessor :from_company, :from => "FromCompany"
|
13
|
+
xml_accessor :from_person, :from => "FromPerson"
|
14
|
+
xml_accessor :from_email, :from => "FromEmail"
|
15
|
+
xml_accessor :to_ean_number, :from => "ToEANNumber"
|
16
|
+
xml_accessor :to_san, :from => "ToSAN"
|
17
|
+
xml_accessor :addressee_identifiers, :from => "AddresseeIdentifier", :as => [Cacofonix::AddresseeIdentifier]
|
18
|
+
xml_accessor :to_company, :from => "ToCompany"
|
19
|
+
xml_accessor :to_person, :from => "ToPerson"
|
20
|
+
xml_accessor :message_number, :from => "MessageNumber"
|
21
|
+
xml_accessor :message_repeat, :from => "MessageRepeat", :as => Integer
|
22
|
+
xml_accessor(:sent_date, :from => "SentDate", :to_xml => Cacofonix::Formatters.yyyymmdd) do |val|
|
23
|
+
begin
|
24
|
+
Date.parse(val)
|
25
|
+
rescue
|
26
|
+
nil
|
27
|
+
end
|
28
|
+
end
|
29
|
+
xml_accessor :message_note, :from => "MessageNote"
|
30
|
+
|
31
|
+
# defaults
|
32
|
+
xml_accessor :default_language_of_text, :from => "DefaultLanguageOfText"
|
33
|
+
xml_accessor :default_price_type_code, :from => "DefaultPriceTypeCode", :as => Integer, :to_xml => Cacofonix::Formatters.two_digit
|
34
|
+
xml_accessor :default_currency_code, :from => "DefaultCurrencyCode"
|
35
|
+
xml_reader :default_linear_unit, :from => "DefaultLinearUnit" # deprecated in ONIX spec
|
36
|
+
xml_reader :default_weight_unit, :from => "DefaultWeightUnit" # deprecated in ONIX spec
|
37
|
+
xml_accessor :default_class_of_trade, :from => "DefaultClassOfTrade"
|
38
|
+
|
39
|
+
def initialize
|
40
|
+
self.sender_identifiers = []
|
41
|
+
self.addressee_identifiers = []
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
@@ -0,0 +1,108 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
module Cacofonix
|
4
|
+
|
5
|
+
# Builds hashes for all code lists in the ONIX spec.
|
6
|
+
#
|
7
|
+
# Use like so:
|
8
|
+
#
|
9
|
+
# Cacofonix::Lists.list(7)
|
10
|
+
# => { "BB" => "Hardback", ... }
|
11
|
+
#
|
12
|
+
# There are also some constants for commonly used lists:
|
13
|
+
#
|
14
|
+
# Cacofonix::Lists::PRODUCT_FORM
|
15
|
+
# => { "BB" => "Hardback", ... }
|
16
|
+
#
|
17
|
+
class Lists
|
18
|
+
include Singleton
|
19
|
+
|
20
|
+
# retrieve a hash with the specified code list
|
21
|
+
#
|
22
|
+
# Cacofonix::Lists.list(7)
|
23
|
+
# => { "BB" => "Hardback", ... }
|
24
|
+
#
|
25
|
+
def self.list(number)
|
26
|
+
self.instance.list(number)
|
27
|
+
end
|
28
|
+
|
29
|
+
# Return a hash with the data for a single code list.
|
30
|
+
#
|
31
|
+
# Number should be a fixnum specifying the list to retrieve:
|
32
|
+
#
|
33
|
+
# Cacofonix::Lists.instance.list(7)
|
34
|
+
# => { "BB" => "Hardback", ... }
|
35
|
+
#
|
36
|
+
def list(number)
|
37
|
+
raise "Invalid list number: #{number}" unless number.to_s.match(/^\d+$/)
|
38
|
+
require File.join("cacofonix", "codelists", number.to_s.rjust(3, "0"))
|
39
|
+
eval("Cacofonix::CodeLists::LIST_#{number}")
|
40
|
+
end
|
41
|
+
|
42
|
+
# Shortcut to retrieve a common code list
|
43
|
+
#
|
44
|
+
def self.audience_code
|
45
|
+
self.instance.list(28)
|
46
|
+
end
|
47
|
+
|
48
|
+
# Shortcut to retrieve a common code list
|
49
|
+
#
|
50
|
+
def self.contributor_role
|
51
|
+
self.instance.list(17)
|
52
|
+
end
|
53
|
+
|
54
|
+
# Shortcut to retrieve a common code list
|
55
|
+
#
|
56
|
+
def self.country_code
|
57
|
+
self.instance.list(91)
|
58
|
+
end
|
59
|
+
|
60
|
+
# Shortcut to retrieve a common code list
|
61
|
+
#
|
62
|
+
def self.language_code
|
63
|
+
self.instance.list(74)
|
64
|
+
end
|
65
|
+
|
66
|
+
# Shortcut to retrieve a common code list
|
67
|
+
#
|
68
|
+
def self.language_role
|
69
|
+
self.instance.list(22)
|
70
|
+
end
|
71
|
+
|
72
|
+
# Shortcut to retrieve a common code list
|
73
|
+
#
|
74
|
+
def self.notification_type
|
75
|
+
self.instance.list(1)
|
76
|
+
end
|
77
|
+
|
78
|
+
# Shortcut to retrieve a common code list
|
79
|
+
#
|
80
|
+
def self.product_availability
|
81
|
+
self.instance.list(65)
|
82
|
+
end
|
83
|
+
|
84
|
+
# Shortcut to retrieve a common code list
|
85
|
+
#
|
86
|
+
def self.product_form
|
87
|
+
self.instance.list(7)
|
88
|
+
end
|
89
|
+
|
90
|
+
# Shortcut to retrieve a common code list
|
91
|
+
#
|
92
|
+
def self.product_form_detail
|
93
|
+
self.instance.list(78)
|
94
|
+
end
|
95
|
+
|
96
|
+
# These are here for backwards compatability with the onix gem <= 0.8.3
|
97
|
+
AUDIENCE_CODE = Cacofonix::Lists.audience_code
|
98
|
+
CONTRIBUTOR_ROLE = Cacofonix::Lists.contributor_role
|
99
|
+
COUNTRY_CODE = Cacofonix::Lists.country_code
|
100
|
+
LANGUAGE_CODE = Cacofonix::Lists.language_code
|
101
|
+
LANGUAGE_ROLE = Cacofonix::Lists.language_role
|
102
|
+
NOTIFICATION_TYPE = Cacofonix::Lists.notification_type
|
103
|
+
PRODUCT_AVAILABILITY = Cacofonix::Lists.product_availability
|
104
|
+
PRODUCT_FORM = Cacofonix::Lists.product_form
|
105
|
+
PRODUCT_FORM_DETAIL = Cacofonix::Lists.product_form_detail
|
106
|
+
|
107
|
+
end
|
108
|
+
end
|
@@ -0,0 +1,166 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
require 'stringio'
|
4
|
+
require "cacofonix/dtds"
|
5
|
+
|
6
|
+
module Cacofonix
|
7
|
+
|
8
|
+
# This is the primary class for reading data from an ONIX file.
|
9
|
+
#
|
10
|
+
# Each ONIX file should contain a single header, and 1 or more products:
|
11
|
+
#
|
12
|
+
# reader = Cacofonix::Reader.new("somefile.xml")
|
13
|
+
#
|
14
|
+
# puts reader.header.inspect
|
15
|
+
#
|
16
|
+
# reader.each do |product|
|
17
|
+
# puts product.inspect
|
18
|
+
# end
|
19
|
+
#
|
20
|
+
# The header will be returned as an Cacofonix::Header object, and the product will
|
21
|
+
# be an Cacofonix::Product.
|
22
|
+
#
|
23
|
+
# The Cacofonix::Product class can be a bit of a hassle to work with, as data can
|
24
|
+
# be nested in it fairly deeply. To wrap all the products returned by the
|
25
|
+
# reader in a shim that provides simple accessor access to common attributes,
|
26
|
+
# pass the shim class as a second argument.
|
27
|
+
#
|
28
|
+
# reader = Cacofonix::Reader.new("somefile.xml", Cacofonix::APAProduct)
|
29
|
+
#
|
30
|
+
# puts reader.header.inspect
|
31
|
+
#
|
32
|
+
# reader.each do |product|
|
33
|
+
# puts product.inspect
|
34
|
+
# end
|
35
|
+
#
|
36
|
+
# APAProduct stands for Australian Publishers Association and provides simple
|
37
|
+
# access to the ONIX attributes that are commonly used in the Australian
|
38
|
+
# market.
|
39
|
+
#
|
40
|
+
# As well as accessing the file header, there are handful of other read only
|
41
|
+
# attributes that might be useful
|
42
|
+
#
|
43
|
+
# reader = Cacofonix::Reader.new("somefile.xml", Cacofonix::APAProduct)
|
44
|
+
#
|
45
|
+
# puts reader.xml_lang
|
46
|
+
# puts reader.xml_version
|
47
|
+
#
|
48
|
+
# Note that ONIX has 1500 valid named entities (such as –) that can
|
49
|
+
# cause the parser to throw an exception because it doesn't recognise them.
|
50
|
+
# To work around this, the parser loads the ONIX DTD. It generally has to
|
51
|
+
# do this over the internet, which slows parsing considerably. To skip DTD
|
52
|
+
# loading (running the risk of parser exceptions), you can pass an option
|
53
|
+
# to the constructor:
|
54
|
+
#
|
55
|
+
# reader = Cacofonix::Reader.new("somefile.xml", Cacofonix::Product, :dtd => false)
|
56
|
+
#
|
57
|
+
# For more information, see http://is.gd/p7fHQq
|
58
|
+
#
|
59
|
+
class Reader
|
60
|
+
include Enumerable
|
61
|
+
|
62
|
+
attr_reader :header, :release
|
63
|
+
attr_reader :xml_lang, :xml_version
|
64
|
+
|
65
|
+
# Options:
|
66
|
+
#
|
67
|
+
# :dtd - if false, then DTD is not loaded before parsing
|
68
|
+
# :interpret - a module (or an array of modules) that should extend
|
69
|
+
# each Product
|
70
|
+
#
|
71
|
+
def initialize(input, product_klass = ::Cacofonix::Product, options = {})
|
72
|
+
@input = input
|
73
|
+
@product_klass = product_klass
|
74
|
+
@options = options || {}
|
75
|
+
|
76
|
+
create_parser
|
77
|
+
|
78
|
+
@release = find_release
|
79
|
+
@header = find_header
|
80
|
+
|
81
|
+
@xml_lang ||= @reader.lang
|
82
|
+
@xml_version ||= @reader.xml_version.to_f
|
83
|
+
end
|
84
|
+
|
85
|
+
# Iterate over all the products in an ONIX file
|
86
|
+
#
|
87
|
+
def each(&block)
|
88
|
+
@reader.each do |node|
|
89
|
+
if @reader.node_type == 1 && @reader.name == "Product"
|
90
|
+
str = @reader.outer_xml
|
91
|
+
product = str.nil? ? @product_klass.new : @product_klass.from_xml(str)
|
92
|
+
product.interpret @options[:interpret]
|
93
|
+
yield product
|
94
|
+
end
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
# Assemble all the products in the ONIX file into an array. Obviously this
|
99
|
+
# will chew through memory with very large ONIX files, so use with care.
|
100
|
+
#
|
101
|
+
def products
|
102
|
+
@products ||= [].tap { |prods| each { |prod| prods << prod } }
|
103
|
+
end
|
104
|
+
|
105
|
+
# Rewind the reader so that you can call 'each' again.
|
106
|
+
#
|
107
|
+
def rewind
|
108
|
+
create_parser
|
109
|
+
end
|
110
|
+
|
111
|
+
def close
|
112
|
+
puts "Reader#close is deprecated."
|
113
|
+
end
|
114
|
+
|
115
|
+
private
|
116
|
+
|
117
|
+
def create_parser
|
118
|
+
Cacofonix::DTDs.apply_libxml_env!
|
119
|
+
|
120
|
+
parser_config = lambda { |cfg|
|
121
|
+
cfg.noent
|
122
|
+
cfg.dtdload unless @options[:dtd] == false
|
123
|
+
}
|
124
|
+
if @input.kind_of?(String)
|
125
|
+
@file = File.open(@input, "r")
|
126
|
+
@reader = Nokogiri::XML::Reader(@file, &parser_config)
|
127
|
+
elsif @input.respond_to?(:read)
|
128
|
+
@reader = Nokogiri::XML::Reader(@input, &parser_config)
|
129
|
+
else
|
130
|
+
raise ArgumentError, "Unable to read from file or IO stream"
|
131
|
+
end
|
132
|
+
end
|
133
|
+
|
134
|
+
def find_release
|
135
|
+
2.times do
|
136
|
+
@reader.read
|
137
|
+
if @reader.node_type == 1 && @reader.name == "ONIXMessage"
|
138
|
+
value = @reader.attributes["release"]
|
139
|
+
if value
|
140
|
+
return BigDecimal(value)
|
141
|
+
else
|
142
|
+
return nil
|
143
|
+
end
|
144
|
+
elsif @reader.node_type == 14
|
145
|
+
return nil
|
146
|
+
end
|
147
|
+
end
|
148
|
+
return nil
|
149
|
+
end
|
150
|
+
|
151
|
+
def find_header
|
152
|
+
100.times do
|
153
|
+
@reader.read
|
154
|
+
if @reader.node_type == 1 && @reader.name == "Header"
|
155
|
+
str = @reader.outer_xml
|
156
|
+
if str.nil?
|
157
|
+
return Cacofonix::Header.new
|
158
|
+
else
|
159
|
+
return Cacofonix::Header.from_xml(str)
|
160
|
+
end
|
161
|
+
end
|
162
|
+
end
|
163
|
+
return nil
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
@@ -0,0 +1,123 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
|
3
|
+
module Cacofonix
|
4
|
+
# The primary way to write a new ONIX file.
|
5
|
+
#
|
6
|
+
# Here's a quick example. The generated file will be nice and boring, as the
|
7
|
+
# header and product objects have no data in them, but you get the idea.
|
8
|
+
#
|
9
|
+
# File.open("output.xml","w") do |output|
|
10
|
+
# header = Cacofonix::Header.new
|
11
|
+
# Cacofonix::Writer.open(output, header) do |writer|
|
12
|
+
# writer << Cacofonix::Product.new
|
13
|
+
# writer << Cacofonix::Product.new
|
14
|
+
# end
|
15
|
+
# end
|
16
|
+
#
|
17
|
+
# If you prefer, you can build your products using the APAProduct shim layer.
|
18
|
+
#
|
19
|
+
# File.open("output.xml","w") do |output|
|
20
|
+
# header = Cacofonix::Header.new
|
21
|
+
# Cacofonix::Writer.open(output, header) do |writer|
|
22
|
+
# writer << Cacofonix::APAProduct.new
|
23
|
+
# writer << Cacofonix::APAProduct.new
|
24
|
+
# end
|
25
|
+
# end
|
26
|
+
#
|
27
|
+
# You can also have the writer build and yield the product to you:
|
28
|
+
#
|
29
|
+
# Cacofonix::Writer.open(output, header, :class => Cacofonix::APAProduct) do |writer|
|
30
|
+
# writer.product do |product|
|
31
|
+
# product.title = "Grimm's Fairy Tales"
|
32
|
+
# product.publication_date = Date.today
|
33
|
+
# end
|
34
|
+
# writer.product do |product|
|
35
|
+
# product.title = "Telling the Truth"
|
36
|
+
# product.publication_date = Date.today - 7
|
37
|
+
# end
|
38
|
+
# end
|
39
|
+
#
|
40
|
+
#
|
41
|
+
# ... which then allows you to use "interpretation modules":
|
42
|
+
#
|
43
|
+
# module MySetters
|
44
|
+
# def set_publication_date_to_xmas
|
45
|
+
# self.publication_date = Date.parse("2001-12-25")
|
46
|
+
# end
|
47
|
+
# end
|
48
|
+
#
|
49
|
+
# Cacofonix::Writer.open(output, header, :interpret => MySetters) do |writer|
|
50
|
+
# writer.product { |product| product.set_publication_date_to_xmas }
|
51
|
+
# end
|
52
|
+
#
|
53
|
+
#
|
54
|
+
class Writer
|
55
|
+
|
56
|
+
DOCTYPE = "http://www.editeur.org/onix/2.1/03/reference/onix-international.dtd"
|
57
|
+
|
58
|
+
# Default constructor.
|
59
|
+
def initialize(output, header, options = {})
|
60
|
+
raise ArgumentError, 'msg must be an Cacofonix::Header object' unless header.kind_of?(Cacofonix::Header)
|
61
|
+
@output = output
|
62
|
+
@header = header
|
63
|
+
@options = options
|
64
|
+
@product_klass = @options[:class] || Cacofonix::Product
|
65
|
+
@finished = false
|
66
|
+
|
67
|
+
start_document
|
68
|
+
end
|
69
|
+
|
70
|
+
# deprecated
|
71
|
+
def start_document
|
72
|
+
puts "Cacofonix::StreamWriter#start_document is no longer required"
|
73
|
+
end
|
74
|
+
|
75
|
+
def << (product)
|
76
|
+
unless product.kind_of?(Cacofonix::Product) || product.kind_of?(Cacofonix::SimpleProduct)
|
77
|
+
raise ArgumentError, 'product must be an Cacofonix::Product or Cacofonix::SimpleProduct'
|
78
|
+
end
|
79
|
+
raise "Can't add products to a finished writer" if finished?
|
80
|
+
|
81
|
+
@output.write(product.to_xml.to_s)
|
82
|
+
@output.write("\n")
|
83
|
+
end
|
84
|
+
|
85
|
+
def product
|
86
|
+
raise ArgumentError, "Block required" unless block_given?
|
87
|
+
product = @product_klass.new
|
88
|
+
product.interpret @options[:interpret]
|
89
|
+
yield product
|
90
|
+
self << product
|
91
|
+
end
|
92
|
+
|
93
|
+
def end_document
|
94
|
+
@output.write("</ONIXMessage>\n")
|
95
|
+
@finished = true
|
96
|
+
end
|
97
|
+
|
98
|
+
def finished?
|
99
|
+
@finished
|
100
|
+
end
|
101
|
+
|
102
|
+
def self.open(output, header, options = {})
|
103
|
+
if block_given?
|
104
|
+
writer = self.new(output, header, options)
|
105
|
+
yield writer
|
106
|
+
writer.end_document
|
107
|
+
else
|
108
|
+
self.new(output, header, options)
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
private
|
113
|
+
|
114
|
+
def start_document
|
115
|
+
@output.write("<?xml version=\"1.0\" encoding=\"utf-8\"?>\n")
|
116
|
+
@output.write("<!DOCTYPE ONIXMessage SYSTEM \"#{DOCTYPE}\">\n")
|
117
|
+
@output.write("<ONIXMessage release=\"2.1\">\n")
|
118
|
+
@output.write(@header.to_xml.to_s)
|
119
|
+
@output.write("\n")
|
120
|
+
end
|
121
|
+
|
122
|
+
end
|
123
|
+
end
|