cacofonix 0.10.0

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.
Files changed (294) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +2 -0
  3. data/.rvmrc +1 -0
  4. data/.travis.yml +10 -0
  5. data/CHANGELOG.md +205 -0
  6. data/CODE_OF_CONDUCT.md +74 -0
  7. data/Gemfile +5 -0
  8. data/LICENSE.txt +22 -0
  9. data/README.md +76 -0
  10. data/Rakefile +6 -0
  11. data/TODO +14 -0
  12. data/bin/onix_extract_codelists +41 -0
  13. data/cacofonix.gemspec +39 -0
  14. data/data/9780194351898.xml +74 -0
  15. data/data/Ashgate Other.xml +382679 -0
  16. data/data/Bookwise_July_2008.xml +21611 -0
  17. data/data/Peribo Onix 0408.xml +17051 -0
  18. data/data/aau.xml +96 -0
  19. data/data/audience_range.xml +9 -0
  20. data/data/contributor.xml +6 -0
  21. data/data/control_chars.xml +74 -0
  22. data/data/entities.xml +78 -0
  23. data/data/extra_entities.xml +65 -0
  24. data/data/header.xml +21 -0
  25. data/data/header_invalid_sentdate.xml +21 -0
  26. data/data/hlasep08.xml +24519 -0
  27. data/data/imprint.xml +5 -0
  28. data/data/iso_8859_1.xml +58 -0
  29. data/data/jul.xml +24783 -0
  30. data/data/language.xml +7 -0
  31. data/data/market_representation.xml +11 -0
  32. data/data/measure.xml +6 -0
  33. data/data/media_file.xml +6 -0
  34. data/data/no_encoding.xml +78 -0
  35. data/data/no_xml_declaration.xml +95 -0
  36. data/data/other_text.xml +5 -0
  37. data/data/price.xml +5 -0
  38. data/data/product.xml +79 -0
  39. data/data/product_identifier.xml +5 -0
  40. data/data/product_invalid_pubdate.xml +42 -0
  41. data/data/publisher.xml +5 -0
  42. data/data/rba_FANT.xml +23 -0
  43. data/data/reference_with_release_attrib.xml +74 -0
  44. data/data/sales_restriction.xml +4 -0
  45. data/data/sales_rights.xml +35 -0
  46. data/data/sender_identifier.xml +5 -0
  47. data/data/series.xml +5 -0
  48. data/data/series_identifier.xml +6 -0
  49. data/data/short_tags.xml +191 -0
  50. data/data/short_tags_ivp.xml +231 -0
  51. data/data/sl_product.xml +81 -0
  52. data/data/stock.xml +5 -0
  53. data/data/subject.xml +6 -0
  54. data/data/supply_detail.xml +18 -0
  55. data/data/title.xml +6 -0
  56. data/data/two_products.xml +114 -0
  57. data/data/usd.xml +175 -0
  58. data/data/utf_16.xml +0 -0
  59. data/data/website.xml +6 -0
  60. data/examples/reader.rb +25 -0
  61. data/examples/reader_apa.rb +22 -0
  62. data/examples/writer.rb +13 -0
  63. data/examples/writer_apa.rb +38 -0
  64. data/lib/cacofonix.rb +151 -0
  65. data/lib/cacofonix/codelists/001.rb +16 -0
  66. data/lib/cacofonix/codelists/002.rb +11 -0
  67. data/lib/cacofonix/codelists/003.rb +13 -0
  68. data/lib/cacofonix/codelists/005.rb +20 -0
  69. data/lib/cacofonix/codelists/006.rb +82 -0
  70. data/lib/cacofonix/codelists/007.rb +129 -0
  71. data/lib/cacofonix/codelists/008.rb +13 -0
  72. data/lib/cacofonix/codelists/009.rb +13 -0
  73. data/lib/cacofonix/codelists/010.rb +52 -0
  74. data/lib/cacofonix/codelists/011.rb +17 -0
  75. data/lib/cacofonix/codelists/012.rb +17 -0
  76. data/lib/cacofonix/codelists/013.rb +13 -0
  77. data/lib/cacofonix/codelists/014.rb +10 -0
  78. data/lib/cacofonix/codelists/015.rb +19 -0
  79. data/lib/cacofonix/codelists/016.rb +12 -0
  80. data/lib/cacofonix/codelists/017.rb +96 -0
  81. data/lib/cacofonix/codelists/018.rb +11 -0
  82. data/lib/cacofonix/codelists/019.rb +13 -0
  83. data/lib/cacofonix/codelists/020.rb +7 -0
  84. data/lib/cacofonix/codelists/021.rb +39 -0
  85. data/lib/cacofonix/codelists/022.rb +15 -0
  86. data/lib/cacofonix/codelists/023.rb +19 -0
  87. data/lib/cacofonix/codelists/024.rb +17 -0
  88. data/lib/cacofonix/codelists/025.rb +35 -0
  89. data/lib/cacofonix/codelists/026.rb +86 -0
  90. data/lib/cacofonix/codelists/027.rb +90 -0
  91. data/lib/cacofonix/codelists/028.rb +14 -0
  92. data/lib/cacofonix/codelists/029.rb +25 -0
  93. data/lib/cacofonix/codelists/030.rb +22 -0
  94. data/lib/cacofonix/codelists/031.rb +9 -0
  95. data/lib/cacofonix/codelists/032.rb +8 -0
  96. data/lib/cacofonix/codelists/033.rb +43 -0
  97. data/lib/cacofonix/codelists/034.rb +21 -0
  98. data/lib/cacofonix/codelists/035.rb +12 -0
  99. data/lib/cacofonix/codelists/036.rb +9 -0
  100. data/lib/cacofonix/codelists/037.rb +12 -0
  101. data/lib/cacofonix/codelists/038.rb +43 -0
  102. data/lib/cacofonix/codelists/039.rb +14 -0
  103. data/lib/cacofonix/codelists/040.rb +12 -0
  104. data/lib/cacofonix/codelists/041.rb +12 -0
  105. data/lib/cacofonix/codelists/042.rb +22 -0
  106. data/lib/cacofonix/codelists/043.rb +12 -0
  107. data/lib/cacofonix/codelists/044.rb +22 -0
  108. data/lib/cacofonix/codelists/045.rb +19 -0
  109. data/lib/cacofonix/codelists/046.rb +15 -0
  110. data/lib/cacofonix/codelists/047.rb +10 -0
  111. data/lib/cacofonix/codelists/048.rb +17 -0
  112. data/lib/cacofonix/codelists/049.rb +91 -0
  113. data/lib/cacofonix/codelists/050.rb +14 -0
  114. data/lib/cacofonix/codelists/051.rb +36 -0
  115. data/lib/cacofonix/codelists/052.rb +7 -0
  116. data/lib/cacofonix/codelists/053.rb +10 -0
  117. data/lib/cacofonix/codelists/054.rb +29 -0
  118. data/lib/cacofonix/codelists/055.rb +23 -0
  119. data/lib/cacofonix/codelists/056.rb +8 -0
  120. data/lib/cacofonix/codelists/057.rb +11 -0
  121. data/lib/cacofonix/codelists/058.rb +29 -0
  122. data/lib/cacofonix/codelists/059.rb +13 -0
  123. data/lib/cacofonix/codelists/060.rb +8 -0
  124. data/lib/cacofonix/codelists/061.rb +9 -0
  125. data/lib/cacofonix/codelists/062.rb +11 -0
  126. data/lib/cacofonix/codelists/063.rb +7 -0
  127. data/lib/cacofonix/codelists/064.rb +19 -0
  128. data/lib/cacofonix/codelists/065.rb +34 -0
  129. data/lib/cacofonix/codelists/066.rb +10 -0
  130. data/lib/cacofonix/codelists/067.rb +8 -0
  131. data/lib/cacofonix/codelists/068.rb +22 -0
  132. data/lib/cacofonix/codelists/069.rb +10 -0
  133. data/lib/cacofonix/codelists/070.rb +8 -0
  134. data/lib/cacofonix/codelists/071.rb +16 -0
  135. data/lib/cacofonix/codelists/072.rb +13 -0
  136. data/lib/cacofonix/codelists/073.rb +42 -0
  137. data/lib/cacofonix/codelists/074.rb +495 -0
  138. data/lib/cacofonix/codelists/075.rb +8 -0
  139. data/lib/cacofonix/codelists/076.rb +18 -0
  140. data/lib/cacofonix/codelists/077.rb +25 -0
  141. data/lib/cacofonix/codelists/078.rb +173 -0
  142. data/lib/cacofonix/codelists/079.rb +25 -0
  143. data/lib/cacofonix/codelists/080.rb +26 -0
  144. data/lib/cacofonix/codelists/081.rb +45 -0
  145. data/lib/cacofonix/codelists/082.rb +23 -0
  146. data/lib/cacofonix/codelists/083.rb +74 -0
  147. data/lib/cacofonix/codelists/084.rb +16 -0
  148. data/lib/cacofonix/codelists/085.rb +29 -0
  149. data/lib/cacofonix/codelists/086.rb +11 -0
  150. data/lib/cacofonix/codelists/087.rb +12 -0
  151. data/lib/cacofonix/codelists/088.rb +7 -0
  152. data/lib/cacofonix/codelists/089.rb +7 -0
  153. data/lib/cacofonix/codelists/090.rb +17 -0
  154. data/lib/cacofonix/codelists/091.rb +257 -0
  155. data/lib/cacofonix/codelists/092.rb +14 -0
  156. data/lib/cacofonix/codelists/093.rb +19 -0
  157. data/lib/cacofonix/codelists/094.rb +9 -0
  158. data/lib/cacofonix/codelists/095.rb +9 -0
  159. data/lib/cacofonix/codelists/096.rb +191 -0
  160. data/lib/cacofonix/codelists/097.rb +7 -0
  161. data/lib/cacofonix/codelists/098.rb +27 -0
  162. data/lib/cacofonix/codelists/099.rb +30 -0
  163. data/lib/cacofonix/codelists/100.rb +12 -0
  164. data/lib/cacofonix/codelists/101.rb +8 -0
  165. data/lib/cacofonix/codelists/102.rb +9 -0
  166. data/lib/cacofonix/codelists/121.rb +164 -0
  167. data/lib/cacofonix/codelists/138.rb +12 -0
  168. data/lib/cacofonix/codelists/139.rb +76 -0
  169. data/lib/cacofonix/codelists/140.rb +13 -0
  170. data/lib/cacofonix/codelists/141.rb +16 -0
  171. data/lib/cacofonix/codelists/142.rb +18 -0
  172. data/lib/cacofonix/codelists/143.rb +13 -0
  173. data/lib/cacofonix/codelists/144.rb +12 -0
  174. data/lib/cacofonix/codelists/145.rb +13 -0
  175. data/lib/cacofonix/codelists/146.rb +9 -0
  176. data/lib/cacofonix/codelists/147.rb +16 -0
  177. data/lib/cacofonix/codelists/148.rb +9 -0
  178. data/lib/cacofonix/codelists/149.rb +10 -0
  179. data/lib/cacofonix/codelists/150.rb +130 -0
  180. data/lib/cacofonix/codelists/151.rb +13 -0
  181. data/lib/cacofonix/codelists/152.rb +8 -0
  182. data/lib/cacofonix/codelists/153.rb +20 -0
  183. data/lib/cacofonix/codelists/154.rb +15 -0
  184. data/lib/cacofonix/codelists/155.rb +11 -0
  185. data/lib/cacofonix/codelists/156.rb +10 -0
  186. data/lib/cacofonix/codelists/157.rb +10 -0
  187. data/lib/cacofonix/codelists/158.rb +32 -0
  188. data/lib/cacofonix/codelists/159.rb +12 -0
  189. data/lib/cacofonix/codelists/160.rb +10 -0
  190. data/lib/cacofonix/codelists/161.rb +9 -0
  191. data/lib/cacofonix/codelists/162.rb +12 -0
  192. data/lib/cacofonix/codelists/163.rb +17 -0
  193. data/lib/cacofonix/codelists/164.rb +11 -0
  194. data/lib/cacofonix/codelists/165.rb +9 -0
  195. data/lib/cacofonix/codelists/166.rb +9 -0
  196. data/lib/cacofonix/codelists/167.rb +9 -0
  197. data/lib/cacofonix/codelists/168.rb +8 -0
  198. data/lib/cacofonix/codelists/169.rb +9 -0
  199. data/lib/cacofonix/codelists/170.rb +7 -0
  200. data/lib/cacofonix/codelists/171.rb +8 -0
  201. data/lib/cacofonix/codelists/172.rb +7 -0
  202. data/lib/cacofonix/codelists/173.rb +8 -0
  203. data/lib/cacofonix/codelists/174.rb +8 -0
  204. data/lib/cacofonix/codelists/175.rb +206 -0
  205. data/lib/cacofonix/codelists/176.rb +20 -0
  206. data/lib/cacofonix/codelists/177.rb +8 -0
  207. data/lib/cacofonix/codelists/178.rb +24 -0
  208. data/lib/cacofonix/codelists/179.rb +7 -0
  209. data/lib/cacofonix/codelists/184.rb +11 -0
  210. data/lib/cacofonix/core/code.rb +106 -0
  211. data/lib/cacofonix/core/element.rb +275 -0
  212. data/lib/cacofonix/core/header.rb +45 -0
  213. data/lib/cacofonix/core/lists.rb +108 -0
  214. data/lib/cacofonix/core/reader.rb +166 -0
  215. data/lib/cacofonix/core/writer.rb +123 -0
  216. data/lib/cacofonix/elements/addressee_identifier.rb +6 -0
  217. data/lib/cacofonix/elements/agent_identifier.rb +6 -0
  218. data/lib/cacofonix/elements/audience.rb +8 -0
  219. data/lib/cacofonix/elements/audience_range.rb +15 -0
  220. data/lib/cacofonix/elements/batch_bonus.rb +7 -0
  221. data/lib/cacofonix/elements/bible.rb +12 -0
  222. data/lib/cacofonix/elements/complexity.rb +7 -0
  223. data/lib/cacofonix/elements/conference.rb +14 -0
  224. data/lib/cacofonix/elements/conference_sponsor.rb +8 -0
  225. data/lib/cacofonix/elements/conference_sponsor_identifier.rb +6 -0
  226. data/lib/cacofonix/elements/contained_item.rb +6 -0
  227. data/lib/cacofonix/elements/content_item.rb +21 -0
  228. data/lib/cacofonix/elements/contributor.rb +19 -0
  229. data/lib/cacofonix/elements/copyright_owner.rb +8 -0
  230. data/lib/cacofonix/elements/copyright_owner_identifier.rb +6 -0
  231. data/lib/cacofonix/elements/copyright_statement.rb +7 -0
  232. data/lib/cacofonix/elements/discount_coded.rb +8 -0
  233. data/lib/cacofonix/elements/extent.rb +8 -0
  234. data/lib/cacofonix/elements/identifier.rb +7 -0
  235. data/lib/cacofonix/elements/illustrations.rb +8 -0
  236. data/lib/cacofonix/elements/imprint.rb +9 -0
  237. data/lib/cacofonix/elements/language.rb +8 -0
  238. data/lib/cacofonix/elements/location_identifier.rb +8 -0
  239. data/lib/cacofonix/elements/main_subject.rb +9 -0
  240. data/lib/cacofonix/elements/market_date.rb +8 -0
  241. data/lib/cacofonix/elements/market_representation.rb +18 -0
  242. data/lib/cacofonix/elements/measure.rb +8 -0
  243. data/lib/cacofonix/elements/media_file.rb +16 -0
  244. data/lib/cacofonix/elements/name.rb +6 -0
  245. data/lib/cacofonix/elements/name_base.rb +17 -0
  246. data/lib/cacofonix/elements/new_supplier.rb +12 -0
  247. data/lib/cacofonix/elements/not_for_sale.rb +13 -0
  248. data/lib/cacofonix/elements/on_order_detail.rb +7 -0
  249. data/lib/cacofonix/elements/other_text.rb +17 -0
  250. data/lib/cacofonix/elements/page_run.rb +7 -0
  251. data/lib/cacofonix/elements/person_date.rb +8 -0
  252. data/lib/cacofonix/elements/person_name_identifier.rb +6 -0
  253. data/lib/cacofonix/elements/price.rb +46 -0
  254. data/lib/cacofonix/elements/prize.rb +10 -0
  255. data/lib/cacofonix/elements/product.rb +155 -0
  256. data/lib/cacofonix/elements/product_base.rb +61 -0
  257. data/lib/cacofonix/elements/product_classification.rb +8 -0
  258. data/lib/cacofonix/elements/product_form_feature.rb +8 -0
  259. data/lib/cacofonix/elements/product_identifier.rb +6 -0
  260. data/lib/cacofonix/elements/professional_affiliation.rb +7 -0
  261. data/lib/cacofonix/elements/publisher.rb +11 -0
  262. data/lib/cacofonix/elements/reissue.rb +9 -0
  263. data/lib/cacofonix/elements/related_product.rb +6 -0
  264. data/lib/cacofonix/elements/religious_text.rb +8 -0
  265. data/lib/cacofonix/elements/religious_text_feature.rb +8 -0
  266. data/lib/cacofonix/elements/sales_outlet.rb +7 -0
  267. data/lib/cacofonix/elements/sales_outlet_identifier.rb +6 -0
  268. data/lib/cacofonix/elements/sales_restriction.rb +7 -0
  269. data/lib/cacofonix/elements/sales_rights.rb +13 -0
  270. data/lib/cacofonix/elements/sender_identifier.rb +6 -0
  271. data/lib/cacofonix/elements/series.rb +11 -0
  272. data/lib/cacofonix/elements/series_identifier.rb +6 -0
  273. data/lib/cacofonix/elements/set.rb +13 -0
  274. data/lib/cacofonix/elements/stock.rb +16 -0
  275. data/lib/cacofonix/elements/stock_quantity_coded.rb +8 -0
  276. data/lib/cacofonix/elements/subject.rb +13 -0
  277. data/lib/cacofonix/elements/supplier_identifier.rb +6 -0
  278. data/lib/cacofonix/elements/supply_detail.rb +37 -0
  279. data/lib/cacofonix/elements/text_item.rb +11 -0
  280. data/lib/cacofonix/elements/text_item_identifier.rb +6 -0
  281. data/lib/cacofonix/elements/title.rb +11 -0
  282. data/lib/cacofonix/elements/website.rb +8 -0
  283. data/lib/cacofonix/elements/work_identifier.rb +6 -0
  284. data/lib/cacofonix/utils/code_list_extractor.rb +112 -0
  285. data/lib/cacofonix/utils/normaliser.rb +125 -0
  286. data/lib/cacofonix/version.rb +5 -0
  287. data/lib/cacofonix/wrappers/apa_product.rb +748 -0
  288. data/lib/cacofonix/wrappers/simple_product.rb +49 -0
  289. data/support/entities.txt +1499 -0
  290. data/support/extract.rb +25 -0
  291. data/support/switch-onix-2.1-short-to-reference.xsl +24 -0
  292. data/support/switch-onix-tagnames-1.1.xsl +25 -0
  293. data/support/switch-onix-tagnames-2.0.xsl +37 -0
  294. 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 &ndash;) 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
@@ -0,0 +1,6 @@
1
+ # coding: utf-8
2
+
3
+ class Cacofonix::AddresseeIdentifier < Cacofonix::Identifier
4
+ xml_name "AddresseeIdentifier"
5
+ onix_code_from_list :addressee_id_type, "AddresseeIDType", :list => 44
6
+ end