pubid 1.15.21 → 2.0.0.alpha.10

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 (863) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE.txt +1 -1
  3. data/README.adoc +2044 -53
  4. data/archived-gems/pubid-ccsds/update_codes.yaml +1 -0
  5. data/archived-gems/pubid-iec/stages.yaml +129 -0
  6. data/archived-gems/pubid-iec/update_codes.yaml +67 -0
  7. data/archived-gems/pubid-ieee/update_codes.yaml +104 -0
  8. data/archived-gems/pubid-iso/stages.yaml +106 -0
  9. data/archived-gems/pubid-iso/update_codes.yaml +4 -0
  10. data/archived-gems/pubid-itu/i18n.yaml +13 -0
  11. data/archived-gems/pubid-itu/series.yaml +42 -0
  12. data/archived-gems/pubid-nist/publishers.yaml +6 -0
  13. data/archived-gems/pubid-nist/series.yaml +121 -0
  14. data/archived-gems/pubid-nist/stages.yaml +16 -0
  15. data/archived-gems/pubid-nist/update_codes.yaml +93 -0
  16. data/archived-gems/pubid-plateau/update_codes.yaml +6 -0
  17. data/data/bipm/update_codes.yaml +9 -0
  18. data/data/ccsds/update_codes.yaml +1 -0
  19. data/data/iec/update_codes.yaml +70 -0
  20. data/data/ieee/update_codes.yaml +210 -0
  21. data/data/iso/update_codes.yaml +21 -0
  22. data/data/nist/series.yaml +155 -0
  23. data/data/nist/update_codes.yaml +122 -0
  24. data/data/plateau/update_codes.yaml +6 -0
  25. data/lib/pubid/adobe/builder.rb +52 -0
  26. data/lib/pubid/adobe/identifier.rb +47 -0
  27. data/lib/pubid/adobe/identifiers/publication.rb +31 -0
  28. data/lib/pubid/adobe/identifiers/tech_note.rb +32 -0
  29. data/lib/pubid/adobe/identifiers.rb +10 -0
  30. data/lib/pubid/adobe/parser.rb +136 -0
  31. data/lib/pubid/adobe/renderer.rb +39 -0
  32. data/lib/pubid/adobe/urn_generator.rb +42 -0
  33. data/lib/pubid/adobe/urn_parser.rb +69 -0
  34. data/lib/pubid/adobe.rb +60 -0
  35. data/lib/pubid/amca/builder.rb +176 -0
  36. data/lib/pubid/amca/identifier.rb +4 -0
  37. data/lib/pubid/amca/identifiers/base.rb +92 -0
  38. data/lib/pubid/amca/identifiers/interpretation.rb +38 -0
  39. data/lib/pubid/amca/identifiers/publication.rb +34 -0
  40. data/lib/pubid/amca/identifiers/standard.rb +20 -0
  41. data/lib/pubid/amca/identifiers.rb +11 -0
  42. data/lib/pubid/amca/parser.rb +153 -0
  43. data/lib/pubid/amca/renderer.rb +82 -0
  44. data/lib/pubid/amca/single_identifier.rb +10 -0
  45. data/lib/pubid/amca/urn_generator.rb +51 -0
  46. data/lib/pubid/amca/urn_parser.rb +28 -0
  47. data/lib/pubid/amca.rb +73 -0
  48. data/lib/pubid/ansi/builder.rb +54 -0
  49. data/lib/pubid/ansi/identifier.rb +31 -0
  50. data/lib/pubid/ansi/identifiers/american_national_standard.rb +13 -0
  51. data/lib/pubid/ansi/identifiers/standard.rb +15 -0
  52. data/lib/pubid/ansi/identifiers.rb +11 -0
  53. data/lib/pubid/ansi/parser.rb +91 -0
  54. data/lib/pubid/ansi/renderer.rb +53 -0
  55. data/lib/pubid/ansi/single_identifier.rb +16 -0
  56. data/lib/pubid/ansi/urn_generator.rb +41 -0
  57. data/lib/pubid/ansi/urn_parser.rb +23 -0
  58. data/lib/pubid/ansi.rb +68 -0
  59. data/lib/pubid/api/builder.rb +58 -0
  60. data/lib/pubid/api/components/code.rb +9 -0
  61. data/lib/pubid/api/identifier.rb +42 -0
  62. data/lib/pubid/api/identifiers/base.rb +12 -0
  63. data/lib/pubid/api/identifiers/bulletin.rb +13 -0
  64. data/lib/pubid/api/identifiers/continuous_operations_standard.rb +13 -0
  65. data/lib/pubid/api/identifiers/mpms.rb +26 -0
  66. data/lib/pubid/api/identifiers/publication.rb +13 -0
  67. data/lib/pubid/api/identifiers/recommended_practice.rb +13 -0
  68. data/lib/pubid/api/identifiers/specification.rb +13 -0
  69. data/lib/pubid/api/identifiers/standard.rb +13 -0
  70. data/lib/pubid/api/identifiers/technical_report.rb +13 -0
  71. data/lib/pubid/api/identifiers/typeless_standard.rb +11 -0
  72. data/lib/pubid/api/identifiers.rb +18 -0
  73. data/lib/pubid/api/parser.rb +140 -0
  74. data/lib/pubid/api/renderer.rb +98 -0
  75. data/lib/pubid/api/single_identifier.rb +24 -0
  76. data/lib/pubid/api/urn_generator.rb +23 -0
  77. data/lib/pubid/api/urn_parser.rb +35 -0
  78. data/lib/pubid/api.rb +68 -0
  79. data/lib/pubid/ashrae/builder.rb +519 -0
  80. data/lib/pubid/ashrae/identifier.rb +8 -0
  81. data/lib/pubid/ashrae/identifiers/addenda_package.rb +42 -0
  82. data/lib/pubid/ashrae/identifiers/addendum.rb +44 -0
  83. data/lib/pubid/ashrae/identifiers/base.rb +119 -0
  84. data/lib/pubid/ashrae/identifiers/combined_addenda.rb +43 -0
  85. data/lib/pubid/ashrae/identifiers/errata.rb +39 -0
  86. data/lib/pubid/ashrae/identifiers/guideline.rb +41 -0
  87. data/lib/pubid/ashrae/identifiers/interpretation.rb +45 -0
  88. data/lib/pubid/ashrae/identifiers/standard.rb +41 -0
  89. data/lib/pubid/ashrae/identifiers.rb +15 -0
  90. data/lib/pubid/ashrae/parser.rb +748 -0
  91. data/lib/pubid/ashrae/renderer.rb +117 -0
  92. data/lib/pubid/ashrae/single_identifier.rb +10 -0
  93. data/lib/pubid/ashrae/supplement_identifier.rb +38 -0
  94. data/lib/pubid/ashrae/urn_generator.rb +57 -0
  95. data/lib/pubid/ashrae/urn_parser.rb +27 -0
  96. data/lib/pubid/ashrae.rb +77 -0
  97. data/lib/pubid/asme/builder.rb +162 -0
  98. data/lib/pubid/asme/components/code.rb +26 -0
  99. data/lib/pubid/asme/identifier.rb +24 -0
  100. data/lib/pubid/asme/identifiers/base.rb +10 -0
  101. data/lib/pubid/asme/identifiers/standard.rb +96 -0
  102. data/lib/pubid/asme/identifiers.rb +10 -0
  103. data/lib/pubid/asme/parser.rb +308 -0
  104. data/lib/pubid/asme/renderer.rb +66 -0
  105. data/lib/pubid/asme/single_identifier.rb +38 -0
  106. data/lib/pubid/asme/urn_generator.rb +133 -0
  107. data/lib/pubid/asme/urn_parser.rb +31 -0
  108. data/lib/pubid/asme.rb +67 -0
  109. data/lib/pubid/astm/builder.rb +166 -0
  110. data/lib/pubid/astm/components/code.rb +42 -0
  111. data/lib/pubid/astm/components.rb +9 -0
  112. data/lib/pubid/astm/identifier.rb +24 -0
  113. data/lib/pubid/astm/identifiers/adjunct.rb +28 -0
  114. data/lib/pubid/astm/identifiers/base.rb +13 -0
  115. data/lib/pubid/astm/identifiers/code_number.rb +81 -0
  116. data/lib/pubid/astm/identifiers/data_series.rb +13 -0
  117. data/lib/pubid/astm/identifiers/iso_dual_published.rb +65 -0
  118. data/lib/pubid/astm/identifiers/manual.rb +23 -0
  119. data/lib/pubid/astm/identifiers/monograph.rb +13 -0
  120. data/lib/pubid/astm/identifiers/research_report.rb +21 -0
  121. data/lib/pubid/astm/identifiers/standard.rb +23 -0
  122. data/lib/pubid/astm/identifiers/technical_report.rb +12 -0
  123. data/lib/pubid/astm/identifiers/work_in_progress.rb +12 -0
  124. data/lib/pubid/astm/identifiers.rb +19 -0
  125. data/lib/pubid/astm/parser.rb +244 -0
  126. data/lib/pubid/astm/renderer.rb +172 -0
  127. data/lib/pubid/astm/single_identifier.rb +47 -0
  128. data/lib/pubid/astm/urn_generator.rb +101 -0
  129. data/lib/pubid/astm/urn_parser.rb +30 -0
  130. data/lib/pubid/astm.rb +55 -0
  131. data/lib/pubid/bipm/builder.rb +163 -0
  132. data/lib/pubid/bipm/identifier.rb +285 -0
  133. data/lib/pubid/bipm/identifiers/committee_document.rb +36 -0
  134. data/lib/pubid/bipm/identifiers/guide.rb +35 -0
  135. data/lib/pubid/bipm/identifiers/meeting.rb +53 -0
  136. data/lib/pubid/bipm/identifiers/mep.rb +33 -0
  137. data/lib/pubid/bipm/identifiers/metrologia_article.rb +48 -0
  138. data/lib/pubid/bipm/identifiers/si_brochure.rb +33 -0
  139. data/lib/pubid/bipm/identifiers.rb +15 -0
  140. data/lib/pubid/bipm/parser.rb +237 -0
  141. data/lib/pubid/bipm/renderer.rb +118 -0
  142. data/lib/pubid/bipm/urn_generator.rb +58 -0
  143. data/lib/pubid/bipm/urn_parser.rb +60 -0
  144. data/lib/pubid/bipm.rb +91 -0
  145. data/lib/pubid/bsi/builder.rb +1495 -0
  146. data/lib/pubid/bsi/components/code.rb +11 -0
  147. data/lib/pubid/bsi/components/date.rb +11 -0
  148. data/lib/pubid/bsi/components/publisher.rb +11 -0
  149. data/lib/pubid/bsi/components/type.rb +11 -0
  150. data/lib/pubid/bsi/identifier.rb +6 -0
  151. data/lib/pubid/bsi/identifiers/addendum_document.rb +30 -0
  152. data/lib/pubid/bsi/identifiers/adopted_european_norm.rb +67 -0
  153. data/lib/pubid/bsi/identifiers/adopted_international_standard.rb +51 -0
  154. data/lib/pubid/bsi/identifiers/aerospace_standard.rb +65 -0
  155. data/lib/pubid/bsi/identifiers/amendment.rb +48 -0
  156. data/lib/pubid/bsi/identifiers/british_industrial_practice.rb +21 -0
  157. data/lib/pubid/bsi/identifiers/british_standard.rb +34 -0
  158. data/lib/pubid/bsi/identifiers/bundled_identifier.rb +40 -0
  159. data/lib/pubid/bsi/identifiers/committee_document.rb +44 -0
  160. data/lib/pubid/bsi/identifiers/consolidated_identifier.rb +84 -0
  161. data/lib/pubid/bsi/identifiers/corrigendum.rb +44 -0
  162. data/lib/pubid/bsi/identifiers/detailed_specification.rb +33 -0
  163. data/lib/pubid/bsi/identifiers/disc.rb +27 -0
  164. data/lib/pubid/bsi/identifiers/draft_document.rb +27 -0
  165. data/lib/pubid/bsi/identifiers/electronic_book.rb +16 -0
  166. data/lib/pubid/bsi/identifiers/expert_commentary.rb +36 -0
  167. data/lib/pubid/bsi/identifiers/explanatory_supplement.rb +35 -0
  168. data/lib/pubid/bsi/identifiers/flex.rb +30 -0
  169. data/lib/pubid/bsi/identifiers/handbook.rb +23 -0
  170. data/lib/pubid/bsi/identifiers/index.rb +30 -0
  171. data/lib/pubid/bsi/identifiers/method.rb +35 -0
  172. data/lib/pubid/bsi/identifiers/national_annex.rb +48 -0
  173. data/lib/pubid/bsi/identifiers/practice_guide.rb +21 -0
  174. data/lib/pubid/bsi/identifiers/publicly_available_specification.rb +27 -0
  175. data/lib/pubid/bsi/identifiers/published_document.rb +27 -0
  176. data/lib/pubid/bsi/identifiers/section.rb +32 -0
  177. data/lib/pubid/bsi/identifiers/set.rb +40 -0
  178. data/lib/pubid/bsi/identifiers/standalone_amendment.rb +40 -0
  179. data/lib/pubid/bsi/identifiers/supplement_document.rb +29 -0
  180. data/lib/pubid/bsi/identifiers/supplementary_index.rb +35 -0
  181. data/lib/pubid/bsi/identifiers/technical_specification.rb +34 -0
  182. data/lib/pubid/bsi/identifiers/test_method.rb +35 -0
  183. data/lib/pubid/bsi/identifiers/value_added_publication.rb +37 -0
  184. data/lib/pubid/bsi/identifiers.rb +51 -0
  185. data/lib/pubid/bsi/model.rb +196 -0
  186. data/lib/pubid/bsi/parser.rb +673 -0
  187. data/lib/pubid/bsi/renderer.rb +1064 -0
  188. data/lib/pubid/bsi/single_identifier.rb +141 -0
  189. data/lib/pubid/bsi/urn_generator.rb +92 -0
  190. data/lib/pubid/bsi/urn_parser.rb +52 -0
  191. data/lib/pubid/bsi.rb +282 -0
  192. data/lib/pubid/builder/base.rb +187 -0
  193. data/lib/pubid/bundled_identifier.rb +134 -0
  194. data/lib/pubid/calconnect/builder.rb +38 -0
  195. data/lib/pubid/calconnect/identifier.rb +121 -0
  196. data/lib/pubid/calconnect/identifiers/standard.rb +29 -0
  197. data/lib/pubid/calconnect/identifiers.rb +9 -0
  198. data/lib/pubid/calconnect/parser.rb +54 -0
  199. data/lib/pubid/calconnect/renderer.rb +36 -0
  200. data/lib/pubid/calconnect/urn_generator.rb +33 -0
  201. data/lib/pubid/calconnect/urn_parser.rb +34 -0
  202. data/lib/pubid/calconnect.rb +82 -0
  203. data/lib/pubid/ccsds/builder.rb +57 -0
  204. data/lib/pubid/ccsds/identifier.rb +76 -0
  205. data/lib/pubid/ccsds/identifiers/base.rb +41 -0
  206. data/lib/pubid/ccsds/identifiers/base_BASE_88929.rb +70 -0
  207. data/lib/pubid/ccsds/identifiers/corrigendum.rb +40 -0
  208. data/lib/pubid/ccsds/identifiers.rb +10 -0
  209. data/lib/pubid/ccsds/parser.rb +73 -0
  210. data/lib/pubid/ccsds/single_identifier.rb +77 -0
  211. data/lib/pubid/ccsds/supplement_identifier.rb +37 -0
  212. data/lib/pubid/ccsds/urn_generator.rb +115 -0
  213. data/lib/pubid/ccsds/urn_parser.rb +20 -0
  214. data/lib/pubid/ccsds.rb +64 -0
  215. data/lib/pubid/cen_cenelec/builder.rb +362 -0
  216. data/lib/pubid/cen_cenelec/identifier.rb +38 -0
  217. data/lib/pubid/cen_cenelec/identifiers/adopted_european_norm.rb +45 -0
  218. data/lib/pubid/cen_cenelec/identifiers/amendment.rb +19 -0
  219. data/lib/pubid/cen_cenelec/identifiers/base.rb +34 -0
  220. data/lib/pubid/cen_cenelec/identifiers/cen_report.rb +29 -0
  221. data/lib/pubid/cen_cenelec/identifiers/cen_workshop_agreement.rb +28 -0
  222. data/lib/pubid/cen_cenelec/identifiers/cenelec_harmonization_document.rb +28 -0
  223. data/lib/pubid/cen_cenelec/identifiers/consolidated_identifier.rb +40 -0
  224. data/lib/pubid/cen_cenelec/identifiers/corrigendum.rb +20 -0
  225. data/lib/pubid/cen_cenelec/identifiers/european_norm.rb +99 -0
  226. data/lib/pubid/cen_cenelec/identifiers/european_prestandard.rb +50 -0
  227. data/lib/pubid/cen_cenelec/identifiers/european_specification.rb +29 -0
  228. data/lib/pubid/cen_cenelec/identifiers/fragment.rb +18 -0
  229. data/lib/pubid/cen_cenelec/identifiers/guide.rb +27 -0
  230. data/lib/pubid/cen_cenelec/identifiers/harmonization_document.rb +28 -0
  231. data/lib/pubid/cen_cenelec/identifiers/technical_report.rb +28 -0
  232. data/lib/pubid/cen_cenelec/identifiers/technical_specification.rb +36 -0
  233. data/lib/pubid/cen_cenelec/identifiers.rb +32 -0
  234. data/lib/pubid/cen_cenelec/parser.rb +144 -0
  235. data/lib/pubid/cen_cenelec/renderer.rb +261 -0
  236. data/lib/pubid/cen_cenelec/single_identifier.rb +49 -0
  237. data/lib/pubid/cen_cenelec/supplement_identifier.rb +47 -0
  238. data/lib/pubid/cen_cenelec/urn_generator.rb +129 -0
  239. data/lib/pubid/cen_cenelec/urn_parser.rb +28 -0
  240. data/lib/pubid/cen_cenelec.rb +208 -0
  241. data/lib/pubid/cie/builder.rb +524 -0
  242. data/lib/pubid/cie/components/language.rb +58 -0
  243. data/lib/pubid/cie/identifier.rb +33 -0
  244. data/lib/pubid/cie/identifiers/bundle.rb +50 -0
  245. data/lib/pubid/cie/identifiers/code_attributes.rb +52 -0
  246. data/lib/pubid/cie/identifiers/conference.rb +37 -0
  247. data/lib/pubid/cie/identifiers/corrigendum.rb +34 -0
  248. data/lib/pubid/cie/identifiers/dual_published.rb +41 -0
  249. data/lib/pubid/cie/identifiers/identical.rb +64 -0
  250. data/lib/pubid/cie/identifiers/joint_published.rb +52 -0
  251. data/lib/pubid/cie/identifiers/proceedings.rb +41 -0
  252. data/lib/pubid/cie/identifiers/standard.rb +93 -0
  253. data/lib/pubid/cie/identifiers/supplement.rb +47 -0
  254. data/lib/pubid/cie/identifiers/tutorial_bundle.rb +24 -0
  255. data/lib/pubid/cie/identifiers.rb +19 -0
  256. data/lib/pubid/cie/parser.rb +396 -0
  257. data/lib/pubid/cie/single_identifier.rb +69 -0
  258. data/lib/pubid/cie/supplement_identifier.rb +39 -0
  259. data/lib/pubid/cie/urn_generator.rb +126 -0
  260. data/lib/pubid/cie/urn_parser.rb +28 -0
  261. data/lib/pubid/cie.rb +83 -0
  262. data/lib/pubid/components/adoption.rb +104 -0
  263. data/lib/pubid/components/code.rb +47 -0
  264. data/lib/pubid/components/date.rb +72 -0
  265. data/lib/pubid/components/edition.rb +35 -0
  266. data/lib/pubid/components/iteration.rb +32 -0
  267. data/lib/pubid/components/language.rb +39 -0
  268. data/lib/pubid/components/locality.rb +19 -0
  269. data/lib/pubid/components/publisher.rb +39 -0
  270. data/lib/pubid/components/relationship.rb +151 -0
  271. data/lib/pubid/components/stage.rb +45 -0
  272. data/lib/pubid/components/supplement.rb +184 -0
  273. data/lib/pubid/components/type.rb +48 -0
  274. data/lib/pubid/components/typed_stage.rb +58 -0
  275. data/lib/pubid/components.rb +19 -0
  276. data/lib/pubid/core/pattern_doc_generator.rb +272 -0
  277. data/lib/pubid/core/update_codes.rb +98 -0
  278. data/lib/pubid/core.rb +8 -0
  279. data/lib/pubid/csa/builder.rb +671 -0
  280. data/lib/pubid/csa/components/code.rb +9 -0
  281. data/lib/pubid/csa/components.rb +9 -0
  282. data/lib/pubid/csa/composite_identifier.rb +38 -0
  283. data/lib/pubid/csa/identifier.rb +570 -0
  284. data/lib/pubid/csa/identifiers/base.rb +10 -0
  285. data/lib/pubid/csa/identifiers/bundled.rb +141 -0
  286. data/lib/pubid/csa/identifiers/canadian_adopted.rb +82 -0
  287. data/lib/pubid/csa/identifiers/cec.rb +66 -0
  288. data/lib/pubid/csa/identifiers/combined.rb +158 -0
  289. data/lib/pubid/csa/identifiers/csa_adopted.rb +78 -0
  290. data/lib/pubid/csa/identifiers/package.rb +65 -0
  291. data/lib/pubid/csa/identifiers/series.rb +23 -0
  292. data/lib/pubid/csa/identifiers/standard.rb +10 -0
  293. data/lib/pubid/csa/identifiers.rb +17 -0
  294. data/lib/pubid/csa/parser.rb +449 -0
  295. data/lib/pubid/csa/renderer.rb +300 -0
  296. data/lib/pubid/csa/single_identifier.rb +119 -0
  297. data/lib/pubid/csa/urn_generator.rb +87 -0
  298. data/lib/pubid/csa/urn_parser.rb +33 -0
  299. data/lib/pubid/csa/wrapper_identifier.rb +64 -0
  300. data/lib/pubid/csa.rb +80 -0
  301. data/lib/pubid/doi/builder.rb +18 -0
  302. data/lib/pubid/doi/identifier.rb +49 -0
  303. data/lib/pubid/doi/identifiers/resource.rb +30 -0
  304. data/lib/pubid/doi/identifiers.rb +9 -0
  305. data/lib/pubid/doi/parser.rb +52 -0
  306. data/lib/pubid/doi/renderer.rb +13 -0
  307. data/lib/pubid/doi.rb +55 -0
  308. data/lib/pubid/easc/builder.rb +55 -0
  309. data/lib/pubid/easc/identifier.rb +59 -0
  310. data/lib/pubid/easc/identifiers/pmg.rb +20 -0
  311. data/lib/pubid/easc/identifiers/rmg.rb +19 -0
  312. data/lib/pubid/easc/identifiers.rb +10 -0
  313. data/lib/pubid/easc/parser.rb +88 -0
  314. data/lib/pubid/easc/renderer.rb +48 -0
  315. data/lib/pubid/easc/urn_generator.rb +46 -0
  316. data/lib/pubid/easc/urn_parser.rb +57 -0
  317. data/lib/pubid/easc.rb +52 -0
  318. data/lib/pubid/ecma/builder.rb +45 -0
  319. data/lib/pubid/ecma/identifier.rb +147 -0
  320. data/lib/pubid/ecma/identifiers/memento.rb +30 -0
  321. data/lib/pubid/ecma/identifiers/standard.rb +31 -0
  322. data/lib/pubid/ecma/identifiers/technical_report.rb +31 -0
  323. data/lib/pubid/ecma/identifiers.rb +11 -0
  324. data/lib/pubid/ecma/parser.rb +76 -0
  325. data/lib/pubid/ecma/renderer.rb +67 -0
  326. data/lib/pubid/ecma/urn_generator.rb +46 -0
  327. data/lib/pubid/ecma/urn_parser.rb +51 -0
  328. data/lib/pubid/ecma.rb +67 -0
  329. data/lib/pubid/errors.rb +79 -0
  330. data/lib/pubid/etsi/builder.rb +142 -0
  331. data/lib/pubid/etsi/components/code.rb +43 -0
  332. data/lib/pubid/etsi/components/version.rb +32 -0
  333. data/lib/pubid/etsi/components.rb +10 -0
  334. data/lib/pubid/etsi/identifier.rb +4 -0
  335. data/lib/pubid/etsi/identifiers/amendment.rb +15 -0
  336. data/lib/pubid/etsi/identifiers/base.rb +74 -0
  337. data/lib/pubid/etsi/identifiers/corrigendum.rb +15 -0
  338. data/lib/pubid/etsi/identifiers/etsi_standard.rb +222 -0
  339. data/lib/pubid/etsi/identifiers/supplement_identifier.rb +123 -0
  340. data/lib/pubid/etsi/identifiers.rb +13 -0
  341. data/lib/pubid/etsi/parser.rb +139 -0
  342. data/lib/pubid/etsi/renderer.rb +48 -0
  343. data/lib/pubid/etsi/urn_generator.rb +76 -0
  344. data/lib/pubid/etsi/urn_parser.rb +34 -0
  345. data/lib/pubid/etsi.rb +71 -0
  346. data/lib/pubid/export/auditor.rb +89 -0
  347. data/lib/pubid/export/exporter.rb +33 -0
  348. data/lib/pubid/export/flavor_exporter.rb +250 -0
  349. data/lib/pubid/export/result.rb +97 -0
  350. data/lib/pubid/export.rb +12 -0
  351. data/lib/pubid/format_detector.rb +16 -0
  352. data/lib/pubid/format_registry.rb +42 -0
  353. data/lib/pubid/gb/builder.rb +45 -0
  354. data/lib/pubid/gb/identifier.rb +67 -0
  355. data/lib/pubid/gb/identifiers/standard.rb +34 -0
  356. data/lib/pubid/gb/identifiers.rb +9 -0
  357. data/lib/pubid/gb/parser.rb +63 -0
  358. data/lib/pubid/gb/renderer.rb +35 -0
  359. data/lib/pubid/gb.rb +87 -0
  360. data/lib/pubid/gost/builder.rb +148 -0
  361. data/lib/pubid/gost/identifier.rb +47 -0
  362. data/lib/pubid/gost/identifiers/foreign_reference.rb +25 -0
  363. data/lib/pubid/gost/identifiers/harmonized.rb +39 -0
  364. data/lib/pubid/gost/identifiers/identical_adoption.rb +39 -0
  365. data/lib/pubid/gost/identifiers/interstate_standard.rb +20 -0
  366. data/lib/pubid/gost/identifiers/national_standard.rb +19 -0
  367. data/lib/pubid/gost/identifiers.rb +13 -0
  368. data/lib/pubid/gost/parser.rb +105 -0
  369. data/lib/pubid/gost/renderer.rb +48 -0
  370. data/lib/pubid/gost/urn_generator.rb +46 -0
  371. data/lib/pubid/gost/urn_parser.rb +52 -0
  372. data/lib/pubid/gost.rb +49 -0
  373. data/lib/pubid/iala/builder.rb +102 -0
  374. data/lib/pubid/iala/identifier.rb +90 -0
  375. data/lib/pubid/iala/identifiers/advice.rb +15 -0
  376. data/lib/pubid/iala/identifiers/annex.rb +57 -0
  377. data/lib/pubid/iala/identifiers/general_assembly.rb +19 -0
  378. data/lib/pubid/iala/identifiers/guideline.rb +17 -0
  379. data/lib/pubid/iala/identifiers/letter.rb +16 -0
  380. data/lib/pubid/iala/identifiers/manual.rb +18 -0
  381. data/lib/pubid/iala/identifiers/model_course.rb +17 -0
  382. data/lib/pubid/iala/identifiers/recommendation.rb +17 -0
  383. data/lib/pubid/iala/identifiers/report.rb +16 -0
  384. data/lib/pubid/iala/identifiers/resolution.rb +16 -0
  385. data/lib/pubid/iala/identifiers/standard.rb +17 -0
  386. data/lib/pubid/iala/identifiers.rb +19 -0
  387. data/lib/pubid/iala/parser.rb +138 -0
  388. data/lib/pubid/iala/renderer.rb +36 -0
  389. data/lib/pubid/iala/urn_generator.rb +49 -0
  390. data/lib/pubid/iala/urn_parser.rb +67 -0
  391. data/lib/pubid/iala.rb +71 -0
  392. data/lib/pubid/iana/builder.rb +22 -0
  393. data/lib/pubid/iana/identifier.rb +140 -0
  394. data/lib/pubid/iana/identifiers/registry.rb +69 -0
  395. data/lib/pubid/iana/identifiers.rb +9 -0
  396. data/lib/pubid/iana/parser.rb +38 -0
  397. data/lib/pubid/iana/renderer.rb +32 -0
  398. data/lib/pubid/iana/urn_generator.rb +19 -0
  399. data/lib/pubid/iana/urn_parser.rb +24 -0
  400. data/lib/pubid/iana.rb +69 -0
  401. data/lib/pubid/identifier.rb +1118 -0
  402. data/lib/pubid/identifier_metadata.rb +148 -0
  403. data/lib/pubid/idf/builder.rb +82 -0
  404. data/lib/pubid/idf/identifier.rb +79 -0
  405. data/lib/pubid/idf/identifiers/amendment.rb +28 -0
  406. data/lib/pubid/idf/identifiers/corrigendum.rb +28 -0
  407. data/lib/pubid/idf/identifiers/international_standard.rb +124 -0
  408. data/lib/pubid/idf/identifiers/reviewed_method.rb +101 -0
  409. data/lib/pubid/idf/identifiers.rb +13 -0
  410. data/lib/pubid/idf/parser.rb +144 -0
  411. data/lib/pubid/idf/renderer.rb +84 -0
  412. data/lib/pubid/idf/single_identifier.rb +19 -0
  413. data/lib/pubid/idf/supplement_identifier.rb +35 -0
  414. data/lib/pubid/idf/urn_generator.rb +49 -0
  415. data/lib/pubid/idf/urn_parser.rb +25 -0
  416. data/lib/pubid/idf.rb +89 -0
  417. data/lib/pubid/iec/builder.rb +458 -0
  418. data/lib/pubid/iec/components/code.rb +36 -0
  419. data/lib/pubid/iec/components/consolidated_amendment.rb +59 -0
  420. data/lib/pubid/iec/components/publisher.rb +35 -0
  421. data/lib/pubid/iec/components/sheet.rb +32 -0
  422. data/lib/pubid/iec/components/trf_info.rb +38 -0
  423. data/lib/pubid/iec/components/vap_suffix.rb +41 -0
  424. data/lib/pubid/iec/components.rb +14 -0
  425. data/lib/pubid/iec/identifier.rb +341 -0
  426. data/lib/pubid/iec/identifiers/amendment.rb +97 -0
  427. data/lib/pubid/iec/identifiers/base.rb +54 -0
  428. data/lib/pubid/iec/identifiers/component_specification.rb +29 -0
  429. data/lib/pubid/iec/identifiers/conformity_assessment.rb +28 -0
  430. data/lib/pubid/iec/identifiers/consolidated_identifier.rb +85 -0
  431. data/lib/pubid/iec/identifiers/corrigendum.rb +93 -0
  432. data/lib/pubid/iec/identifiers/fragment_identifier.rb +148 -0
  433. data/lib/pubid/iec/identifiers/guide.rb +86 -0
  434. data/lib/pubid/iec/identifiers/international_standard.rb +162 -0
  435. data/lib/pubid/iec/identifiers/interpretation_sheet.rb +103 -0
  436. data/lib/pubid/iec/identifiers/operational_document.rb +29 -0
  437. data/lib/pubid/iec/identifiers/publicly_available_specification.rb +88 -0
  438. data/lib/pubid/iec/identifiers/sheet_identifier.rb +68 -0
  439. data/lib/pubid/iec/identifiers/societal_technology_trend_report.rb +30 -0
  440. data/lib/pubid/iec/identifiers/systems_reference_document.rb +29 -0
  441. data/lib/pubid/iec/identifiers/technical_group.rb +30 -0
  442. data/lib/pubid/iec/identifiers/technical_report.rb +114 -0
  443. data/lib/pubid/iec/identifiers/technical_specification.rb +114 -0
  444. data/lib/pubid/iec/identifiers/technology_report.rb +28 -0
  445. data/lib/pubid/iec/identifiers/test_report_form.rb +35 -0
  446. data/lib/pubid/iec/identifiers/vap_identifier.rb +76 -0
  447. data/lib/pubid/iec/identifiers/white_paper.rb +29 -0
  448. data/lib/pubid/iec/identifiers/working_document.rb +62 -0
  449. data/lib/pubid/iec/identifiers.rb +31 -0
  450. data/lib/pubid/iec/parser.rb +443 -0
  451. data/lib/pubid/iec/renderer.rb +267 -0
  452. data/lib/pubid/iec/rendering_style.rb +113 -0
  453. data/lib/pubid/iec/single_identifier.rb +72 -0
  454. data/lib/pubid/iec/supplement_identifier.rb +178 -0
  455. data/lib/pubid/iec/urn_generator.rb +245 -0
  456. data/lib/pubid/iec/urn_parser.rb +128 -0
  457. data/lib/pubid/iec.rb +64 -0
  458. data/lib/pubid/ieee/aiee/builder.rb +85 -0
  459. data/lib/pubid/ieee/aiee/identifier.rb +89 -0
  460. data/lib/pubid/ieee/aiee/parser.rb +130 -0
  461. data/lib/pubid/ieee/aiee.rb +11 -0
  462. data/lib/pubid/ieee/builder.rb +1554 -0
  463. data/lib/pubid/ieee/compaction.rb +121 -0
  464. data/lib/pubid/ieee/components/code.rb +110 -0
  465. data/lib/pubid/ieee/components/draft.rb +147 -0
  466. data/lib/pubid/ieee/components/relationship.rb +13 -0
  467. data/lib/pubid/ieee/components/typed_stage.rb +100 -0
  468. data/lib/pubid/ieee/identifier.rb +5 -0
  469. data/lib/pubid/ieee/identifiers/adopted_standard.rb +81 -0
  470. data/lib/pubid/ieee/identifiers/amendment.rb +40 -0
  471. data/lib/pubid/ieee/identifiers/base.rb +384 -0
  472. data/lib/pubid/ieee/identifiers/code_number.rb +82 -0
  473. data/lib/pubid/ieee/identifiers/conformance_identifier.rb +29 -0
  474. data/lib/pubid/ieee/identifiers/corrigendum.rb +40 -0
  475. data/lib/pubid/ieee/identifiers/csa_dual_published.rb +62 -0
  476. data/lib/pubid/ieee/identifiers/dual_identifier.rb +14 -0
  477. data/lib/pubid/ieee/identifiers/dual_published.rb +79 -0
  478. data/lib/pubid/ieee/identifiers/iec_ieee_copublished.rb +115 -0
  479. data/lib/pubid/ieee/identifiers/interpretation_identifier.rb +48 -0
  480. data/lib/pubid/ieee/identifiers/joint_development.rb +223 -0
  481. data/lib/pubid/ieee/identifiers/multi_numbered_identifier.rb +85 -0
  482. data/lib/pubid/ieee/identifiers/nesc/base.rb +127 -0
  483. data/lib/pubid/ieee/identifiers/nesc/draft.rb +43 -0
  484. data/lib/pubid/ieee/identifiers/nesc/edition.rb +32 -0
  485. data/lib/pubid/ieee/identifiers/nesc/handbook.rb +43 -0
  486. data/lib/pubid/ieee/identifiers/nesc/redline.rb +35 -0
  487. data/lib/pubid/ieee/identifiers/nesc/standard.rb +41 -0
  488. data/lib/pubid/ieee/identifiers/nesc.rb +16 -0
  489. data/lib/pubid/ieee/identifiers/parenthetical_identifier.rb +14 -0
  490. data/lib/pubid/ieee/identifiers/project_draft_identifier.rb +49 -0
  491. data/lib/pubid/ieee/identifiers/redlined_standard.rb +26 -0
  492. data/lib/pubid/ieee/identifiers/si_standard.rb +38 -0
  493. data/lib/pubid/ieee/identifiers/standard.rb +44 -0
  494. data/lib/pubid/ieee/identifiers/supplement_identifier.rb +42 -0
  495. data/lib/pubid/ieee/identifiers.rb +34 -0
  496. data/lib/pubid/ieee/ire/builder.rb +62 -0
  497. data/lib/pubid/ieee/ire/identifier.rb +73 -0
  498. data/lib/pubid/ieee/ire/parser.rb +91 -0
  499. data/lib/pubid/ieee/ire.rb +11 -0
  500. data/lib/pubid/ieee/nesc/builder.rb +114 -0
  501. data/lib/pubid/ieee/nesc/parser.rb +155 -0
  502. data/lib/pubid/ieee/nesc.rb +10 -0
  503. data/lib/pubid/ieee/parser.rb +1644 -0
  504. data/lib/pubid/ieee/pre_parser.rb +301 -0
  505. data/lib/pubid/ieee/renderer.rb +408 -0
  506. data/lib/pubid/ieee/typed_stages.rb +183 -0
  507. data/lib/pubid/ieee/urn_generator.rb +215 -0
  508. data/lib/pubid/ieee/urn_parser.rb +34 -0
  509. data/lib/pubid/ieee.rb +163 -0
  510. data/lib/pubid/ieee_debug.rb +30 -0
  511. data/lib/pubid/ietf/builder.rb +78 -0
  512. data/lib/pubid/ietf/identifier.rb +5 -0
  513. data/lib/pubid/ietf/identifiers/base.rb +72 -0
  514. data/lib/pubid/ietf/identifiers/bcp.rb +36 -0
  515. data/lib/pubid/ietf/identifiers/fyi.rb +36 -0
  516. data/lib/pubid/ietf/identifiers/internet_draft.rb +45 -0
  517. data/lib/pubid/ietf/identifiers/rfc.rb +27 -0
  518. data/lib/pubid/ietf/identifiers/serialization.rb +51 -0
  519. data/lib/pubid/ietf/identifiers/std.rb +36 -0
  520. data/lib/pubid/ietf/identifiers.rb +14 -0
  521. data/lib/pubid/ietf/parser.rb +61 -0
  522. data/lib/pubid/ietf/renderer.rb +64 -0
  523. data/lib/pubid/ietf/urn_generator.rb +37 -0
  524. data/lib/pubid/ietf/urn_parser.rb +43 -0
  525. data/lib/pubid/ietf.rb +85 -0
  526. data/lib/pubid/iho/builder.rb +37 -0
  527. data/lib/pubid/iho/identifier.rb +7 -0
  528. data/lib/pubid/iho/identifiers/base.rb +75 -0
  529. data/lib/pubid/iho/identifiers/bibliographic.rb +16 -0
  530. data/lib/pubid/iho/identifiers/circular_letter.rb +15 -0
  531. data/lib/pubid/iho/identifiers/miscellaneous.rb +16 -0
  532. data/lib/pubid/iho/identifiers/publication.rb +15 -0
  533. data/lib/pubid/iho/identifiers/standard.rb +15 -0
  534. data/lib/pubid/iho/identifiers.rb +13 -0
  535. data/lib/pubid/iho/parser.rb +68 -0
  536. data/lib/pubid/iho/renderer.rb +30 -0
  537. data/lib/pubid/iho/urn_generator.rb +29 -0
  538. data/lib/pubid/iho/urn_parser.rb +58 -0
  539. data/lib/pubid/iho.rb +77 -0
  540. data/lib/pubid/isbn/builder.rb +44 -0
  541. data/lib/pubid/isbn/check_digit.rb +53 -0
  542. data/lib/pubid/isbn/identifier.rb +81 -0
  543. data/lib/pubid/isbn/identifiers/book.rb +30 -0
  544. data/lib/pubid/isbn/identifiers.rb +9 -0
  545. data/lib/pubid/isbn/parser.rb +45 -0
  546. data/lib/pubid/isbn/renderer.rb +16 -0
  547. data/lib/pubid/isbn.rb +52 -0
  548. data/lib/pubid/iso/builder.rb +316 -0
  549. data/lib/pubid/iso/bundled_identifier.rb +138 -0
  550. data/lib/pubid/iso/combined_identifier.rb +24 -0
  551. data/lib/pubid/iso/components/code.rb +24 -0
  552. data/lib/pubid/iso/components/publisher.rb +62 -0
  553. data/lib/pubid/iso/components.rb +10 -0
  554. data/lib/pubid/iso/format_resolver.rb +45 -0
  555. data/lib/pubid/iso/identifier.rb +318 -0
  556. data/lib/pubid/iso/identifiers/addendum.rb +107 -0
  557. data/lib/pubid/iso/identifiers/amendment.rb +132 -0
  558. data/lib/pubid/iso/identifiers/corrigendum.rb +108 -0
  559. data/lib/pubid/iso/identifiers/data.rb +75 -0
  560. data/lib/pubid/iso/identifiers/directives.rb +65 -0
  561. data/lib/pubid/iso/identifiers/directives_supplement.rb +148 -0
  562. data/lib/pubid/iso/identifiers/extract.rb +30 -0
  563. data/lib/pubid/iso/identifiers/guide.rb +99 -0
  564. data/lib/pubid/iso/identifiers/international_standard.rb +168 -0
  565. data/lib/pubid/iso/identifiers/international_standardized_profile.rb +94 -0
  566. data/lib/pubid/iso/identifiers/international_workshop_agreement.rb +95 -0
  567. data/lib/pubid/iso/identifiers/pas.rb +93 -0
  568. data/lib/pubid/iso/identifiers/recommendation.rb +45 -0
  569. data/lib/pubid/iso/identifiers/supplement.rb +95 -0
  570. data/lib/pubid/iso/identifiers/tc_document.rb +137 -0
  571. data/lib/pubid/iso/identifiers/technical_report.rb +103 -0
  572. data/lib/pubid/iso/identifiers/technical_specification.rb +102 -0
  573. data/lib/pubid/iso/identifiers/technology_trends_assessments.rb +95 -0
  574. data/lib/pubid/iso/identifiers.rb +32 -0
  575. data/lib/pubid/iso/normalizer.rb +89 -0
  576. data/lib/pubid/iso/parser.rb +534 -0
  577. data/lib/pubid/iso/rendering_style.rb +120 -0
  578. data/lib/pubid/iso/single_identifier.rb +60 -0
  579. data/lib/pubid/iso/supplement_identifier.rb +53 -0
  580. data/lib/pubid/iso/urn_generator.rb +313 -0
  581. data/lib/pubid/iso/urn_parser.rb +442 -0
  582. data/lib/pubid/iso/utilities.rb +86 -0
  583. data/lib/pubid/iso.rb +236 -0
  584. data/lib/pubid/itu/builder.rb +360 -0
  585. data/lib/pubid/itu/components/code.rb +84 -0
  586. data/lib/pubid/itu/components/designation.rb +35 -0
  587. data/lib/pubid/itu/components/sector.rb +46 -0
  588. data/lib/pubid/itu/components/series.rb +25 -0
  589. data/lib/pubid/itu/components.rb +12 -0
  590. data/lib/pubid/itu/i18n.rb +9 -0
  591. data/lib/pubid/itu/i18n.yaml +30 -0
  592. data/lib/pubid/itu/identifier.rb +4 -0
  593. data/lib/pubid/itu/identifiers/addendum.rb +15 -0
  594. data/lib/pubid/itu/identifiers/amendment.rb +19 -0
  595. data/lib/pubid/itu/identifiers/annex.rb +83 -0
  596. data/lib/pubid/itu/identifiers/annex_of_recommendation.rb +87 -0
  597. data/lib/pubid/itu/identifiers/appendix_of_recommendation.rb +92 -0
  598. data/lib/pubid/itu/identifiers/base.rb +482 -0
  599. data/lib/pubid/itu/identifiers/combined_identifier.rb +121 -0
  600. data/lib/pubid/itu/identifiers/corrigendum.rb +35 -0
  601. data/lib/pubid/itu/identifiers/errata.rb +15 -0
  602. data/lib/pubid/itu/identifiers/handbook.rb +38 -0
  603. data/lib/pubid/itu/identifiers/question.rb +63 -0
  604. data/lib/pubid/itu/identifiers/recommendation.rb +15 -0
  605. data/lib/pubid/itu/identifiers/report.rb +39 -0
  606. data/lib/pubid/itu/identifiers/special_publication.rb +31 -0
  607. data/lib/pubid/itu/identifiers/standard_serialization.rb +58 -0
  608. data/lib/pubid/itu/identifiers/supplement.rb +149 -0
  609. data/lib/pubid/itu/identifiers.rb +25 -0
  610. data/lib/pubid/itu/model.rb +111 -0
  611. data/lib/pubid/itu/parser.rb +679 -0
  612. data/lib/pubid/itu/urn_generator.rb +135 -0
  613. data/lib/pubid/itu/urn_parser.rb +31 -0
  614. data/lib/pubid/itu.rb +78 -0
  615. data/lib/pubid/jcgm/builder.rb +106 -0
  616. data/lib/pubid/jcgm/components/publisher.rb +20 -0
  617. data/lib/pubid/jcgm/components.rb +9 -0
  618. data/lib/pubid/jcgm/identifier.rb +21 -0
  619. data/lib/pubid/jcgm/identifiers/amendment.rb +24 -0
  620. data/lib/pubid/jcgm/identifiers/corrigendum.rb +34 -0
  621. data/lib/pubid/jcgm/identifiers/guide.rb +21 -0
  622. data/lib/pubid/jcgm/identifiers/gum_guide.rb +39 -0
  623. data/lib/pubid/jcgm/identifiers/meeting.rb +47 -0
  624. data/lib/pubid/jcgm/identifiers.rb +13 -0
  625. data/lib/pubid/jcgm/parser.rb +151 -0
  626. data/lib/pubid/jcgm/renderer.rb +89 -0
  627. data/lib/pubid/jcgm/single_identifier.rb +118 -0
  628. data/lib/pubid/jcgm/supplement_identifier.rb +51 -0
  629. data/lib/pubid/jcgm/urn_generator.rb +116 -0
  630. data/lib/pubid/jcgm/urn_parser.rb +177 -0
  631. data/lib/pubid/jcgm.rb +86 -0
  632. data/lib/pubid/jis/builder.rb +116 -0
  633. data/lib/pubid/jis/identifier.rb +194 -0
  634. data/lib/pubid/jis/identifiers/amendment.rb +16 -0
  635. data/lib/pubid/jis/identifiers/corrigendum.rb +16 -0
  636. data/lib/pubid/jis/identifiers/explanation.rb +22 -0
  637. data/lib/pubid/jis/identifiers/japanese_industrial_standard.rb +16 -0
  638. data/lib/pubid/jis/identifiers/standard.rb +28 -0
  639. data/lib/pubid/jis/identifiers/technical_report.rb +32 -0
  640. data/lib/pubid/jis/identifiers/technical_specification.rb +32 -0
  641. data/lib/pubid/jis/identifiers.rb +17 -0
  642. data/lib/pubid/jis/parser.rb +135 -0
  643. data/lib/pubid/jis/renderer.rb +69 -0
  644. data/lib/pubid/jis/single_identifier.rb +31 -0
  645. data/lib/pubid/jis/supplement_identifier.rb +50 -0
  646. data/lib/pubid/jis/urn_generator.rb +25 -0
  647. data/lib/pubid/jis/urn_parser.rb +23 -0
  648. data/lib/pubid/jis.rb +69 -0
  649. data/lib/pubid/lutaml/no_store_registration.rb +30 -0
  650. data/lib/pubid/nist/builder.rb +481 -0
  651. data/lib/pubid/nist/caster.rb +1234 -0
  652. data/lib/pubid/nist/circular_supplement_builder.rb +293 -0
  653. data/lib/pubid/nist/components/code.rb +27 -0
  654. data/lib/pubid/nist/components/edition.rb +134 -0
  655. data/lib/pubid/nist/components/issue_number.rb +28 -0
  656. data/lib/pubid/nist/components/part.rb +77 -0
  657. data/lib/pubid/nist/components/stage.rb +53 -0
  658. data/lib/pubid/nist/components/supplement.rb +191 -0
  659. data/lib/pubid/nist/components/translation.rb +42 -0
  660. data/lib/pubid/nist/components/update.rb +103 -0
  661. data/lib/pubid/nist/components/version.rb +35 -0
  662. data/lib/pubid/nist/components/volume.rb +32 -0
  663. data/lib/pubid/nist/components.rb +18 -0
  664. data/lib/pubid/nist/configuration.rb +87 -0
  665. data/lib/pubid/nist/identifier.rb +8 -0
  666. data/lib/pubid/nist/identifiers/base.rb +744 -0
  667. data/lib/pubid/nist/identifiers/circular.rb +80 -0
  668. data/lib/pubid/nist/identifiers/circular_supplement.rb +60 -0
  669. data/lib/pubid/nist/identifiers/commercial_standard.rb +42 -0
  670. data/lib/pubid/nist/identifiers/commercial_standard_emergency.rb +58 -0
  671. data/lib/pubid/nist/identifiers/commercial_standards_monthly.rb +69 -0
  672. data/lib/pubid/nist/identifiers/crpl_report.rb +138 -0
  673. data/lib/pubid/nist/identifiers/dated_document.rb +49 -0
  674. data/lib/pubid/nist/identifiers/federal_information_processing_standards.rb +95 -0
  675. data/lib/pubid/nist/identifiers/grant_contractor_report.rb +36 -0
  676. data/lib/pubid/nist/identifiers/handbook.rb +58 -0
  677. data/lib/pubid/nist/identifiers/internal_report.rb +64 -0
  678. data/lib/pubid/nist/identifiers/letter_circular.rb +46 -0
  679. data/lib/pubid/nist/identifiers/miscellaneous_publication.rb +74 -0
  680. data/lib/pubid/nist/identifiers/monograph.rb +80 -0
  681. data/lib/pubid/nist/identifiers/ncstar.rb +41 -0
  682. data/lib/pubid/nist/identifiers/nsrds.rb +41 -0
  683. data/lib/pubid/nist/identifiers/owmwp.rb +35 -0
  684. data/lib/pubid/nist/identifiers/report.rb +77 -0
  685. data/lib/pubid/nist/identifiers/special_publication.rb +46 -0
  686. data/lib/pubid/nist/identifiers/technical_note.rb +91 -0
  687. data/lib/pubid/nist/identifiers.rb +33 -0
  688. data/lib/pubid/nist/parser.rb +752 -0
  689. data/lib/pubid/nist/parser_output_normalizer.rb +233 -0
  690. data/lib/pubid/nist/preprocessor.rb +443 -0
  691. data/lib/pubid/nist/renderer.rb +43 -0
  692. data/lib/pubid/nist/router.rb +149 -0
  693. data/lib/pubid/nist/series/base.rb +58 -0
  694. data/lib/pubid/nist/series/crpl.rb +13 -0
  695. data/lib/pubid/nist/series/fips.rb +14 -0
  696. data/lib/pubid/nist/series/ir.rb +57 -0
  697. data/lib/pubid/nist/series/letter_preserving.rb +15 -0
  698. data/lib/pubid/nist/series/mono.rb +19 -0
  699. data/lib/pubid/nist/series/ncstar.rb +20 -0
  700. data/lib/pubid/nist/series.rb +49 -0
  701. data/lib/pubid/nist/supplement_identifier.rb +84 -0
  702. data/lib/pubid/nist/urn_generator.rb +133 -0
  703. data/lib/pubid/nist/urn_parser.rb +67 -0
  704. data/lib/pubid/nist.rb +138 -0
  705. data/lib/pubid/oasis/builder.rb +79 -0
  706. data/lib/pubid/oasis/identifier.rb +160 -0
  707. data/lib/pubid/oasis/identifiers/standard.rb +29 -0
  708. data/lib/pubid/oasis/identifiers.rb +9 -0
  709. data/lib/pubid/oasis/parser.rb +34 -0
  710. data/lib/pubid/oasis/renderer.rb +29 -0
  711. data/lib/pubid/oasis/urn_generator.rb +25 -0
  712. data/lib/pubid/oasis/urn_parser.rb +22 -0
  713. data/lib/pubid/oasis.rb +79 -0
  714. data/lib/pubid/ogc/builder.rb +33 -0
  715. data/lib/pubid/ogc/identifier.rb +81 -0
  716. data/lib/pubid/ogc/identifiers/document.rb +26 -0
  717. data/lib/pubid/ogc/identifiers.rb +10 -0
  718. data/lib/pubid/ogc/parser.rb +40 -0
  719. data/lib/pubid/ogc/renderer.rb +33 -0
  720. data/lib/pubid/ogc/urn_generator.rb +14 -0
  721. data/lib/pubid/ogc/urn_parser.rb +22 -0
  722. data/lib/pubid/ogc.rb +71 -0
  723. data/lib/pubid/oiml/builder.rb +270 -0
  724. data/lib/pubid/oiml/components/code.rb +37 -0
  725. data/lib/pubid/oiml/components.rb +9 -0
  726. data/lib/pubid/oiml/identifier.rb +64 -0
  727. data/lib/pubid/oiml/identifiers/amendment.rb +13 -0
  728. data/lib/pubid/oiml/identifiers/annex.rb +29 -0
  729. data/lib/pubid/oiml/identifiers/basic_publication.rb +15 -0
  730. data/lib/pubid/oiml/identifiers/bulletin.rb +137 -0
  731. data/lib/pubid/oiml/identifiers/code_number.rb +90 -0
  732. data/lib/pubid/oiml/identifiers/document.rb +15 -0
  733. data/lib/pubid/oiml/identifiers/errata.rb +15 -0
  734. data/lib/pubid/oiml/identifiers/expert_report.rb +15 -0
  735. data/lib/pubid/oiml/identifiers/guide.rb +15 -0
  736. data/lib/pubid/oiml/identifiers/recommendation.rb +15 -0
  737. data/lib/pubid/oiml/identifiers/seminar_report.rb +15 -0
  738. data/lib/pubid/oiml/identifiers/vocabulary.rb +15 -0
  739. data/lib/pubid/oiml/identifiers.rb +20 -0
  740. data/lib/pubid/oiml/parser.rb +274 -0
  741. data/lib/pubid/oiml/renderer.rb +232 -0
  742. data/lib/pubid/oiml/single_identifier.rb +113 -0
  743. data/lib/pubid/oiml/supplement_identifier.rb +88 -0
  744. data/lib/pubid/oiml/urn_generator.rb +78 -0
  745. data/lib/pubid/oiml/urn_parser.rb +39 -0
  746. data/lib/pubid/oiml.rb +81 -0
  747. data/lib/pubid/omg/builder.rb +19 -0
  748. data/lib/pubid/omg/identifier.rb +47 -0
  749. data/lib/pubid/omg/identifiers/specification.rb +32 -0
  750. data/lib/pubid/omg/identifiers.rb +9 -0
  751. data/lib/pubid/omg/parser.rb +40 -0
  752. data/lib/pubid/omg/renderer.rb +19 -0
  753. data/lib/pubid/omg.rb +51 -0
  754. data/lib/pubid/parser/common_parse_methods.rb +13 -0
  755. data/lib/pubid/parser/common_parse_rules.rb +56 -0
  756. data/lib/pubid/parser/grammar.rb +74 -0
  757. data/lib/pubid/parser.rb +9 -0
  758. data/lib/pubid/parsers/base.rb +11 -0
  759. data/lib/pubid/parsers/mr_string.rb +206 -0
  760. data/lib/pubid/plateau/builder.rb +54 -0
  761. data/lib/pubid/plateau/identifier.rb +4 -0
  762. data/lib/pubid/plateau/identifiers/annex.rb +16 -0
  763. data/lib/pubid/plateau/identifiers/base.rb +55 -0
  764. data/lib/pubid/plateau/identifiers/handbook.rb +28 -0
  765. data/lib/pubid/plateau/identifiers/technical_report.rb +16 -0
  766. data/lib/pubid/plateau/identifiers.rb +11 -0
  767. data/lib/pubid/plateau/parser.rb +73 -0
  768. data/lib/pubid/plateau/renderer.rb +51 -0
  769. data/lib/pubid/plateau/supplement_identifier.rb +68 -0
  770. data/lib/pubid/plateau/urn_generator.rb +29 -0
  771. data/lib/pubid/plateau/urn_parser.rb +43 -0
  772. data/lib/pubid/plateau.rb +82 -0
  773. data/lib/pubid/prefixes_support.rb +51 -0
  774. data/lib/pubid/renderers/annotator.rb +233 -0
  775. data/lib/pubid/renderers/base.rb +66 -0
  776. data/lib/pubid/renderers/directives_renderer.rb +75 -0
  777. data/lib/pubid/renderers/guide_renderer.rb +26 -0
  778. data/lib/pubid/renderers/human_readable.rb +83 -0
  779. data/lib/pubid/renderers/iwa_renderer.rb +20 -0
  780. data/lib/pubid/renderers/mr_string.rb +64 -0
  781. data/lib/pubid/renderers/supplement_renderer.rb +36 -0
  782. data/lib/pubid/renderers/urn.rb +11 -0
  783. data/lib/pubid/renderers.rb +15 -0
  784. data/lib/pubid/rendering/context.rb +168 -0
  785. data/lib/pubid/rendering/date.rb +27 -0
  786. data/lib/pubid/rendering/language.rb +21 -0
  787. data/lib/pubid/rendering/numbering.rb +42 -0
  788. data/lib/pubid/rendering/publisher.rb +25 -0
  789. data/lib/pubid/rendering/stage.rb +38 -0
  790. data/lib/pubid/rendering/supplement.rb +46 -0
  791. data/lib/pubid/rendering.rb +13 -0
  792. data/lib/pubid/sae/builder.rb +32 -0
  793. data/lib/pubid/sae/components/code.rb +9 -0
  794. data/lib/pubid/sae/components/date.rb +27 -0
  795. data/lib/pubid/sae/components/type.rb +23 -0
  796. data/lib/pubid/sae/components.rb +11 -0
  797. data/lib/pubid/sae/identifier.rb +4 -0
  798. data/lib/pubid/sae/identifiers/base.rb +47 -0
  799. data/lib/pubid/sae/identifiers.rb +8 -0
  800. data/lib/pubid/sae/parser.rb +55 -0
  801. data/lib/pubid/sae/renderer.rb +36 -0
  802. data/lib/pubid/sae/urn_generator.rb +30 -0
  803. data/lib/pubid/sae/urn_parser.rb +36 -0
  804. data/lib/pubid/sae.rb +66 -0
  805. data/lib/pubid/tgpp/builder.rb +41 -0
  806. data/lib/pubid/tgpp/identifier.rb +107 -0
  807. data/lib/pubid/tgpp/identifiers/technical_report.rb +32 -0
  808. data/lib/pubid/tgpp/identifiers/technical_specification.rb +33 -0
  809. data/lib/pubid/tgpp/identifiers.rb +11 -0
  810. data/lib/pubid/tgpp/parser.rb +78 -0
  811. data/lib/pubid/tgpp/renderer.rb +52 -0
  812. data/lib/pubid/tgpp/urn_generator.rb +39 -0
  813. data/lib/pubid/tgpp/urn_parser.rb +30 -0
  814. data/lib/pubid/tgpp.rb +83 -0
  815. data/lib/pubid/type_resolver.rb +59 -0
  816. data/lib/pubid/un/builder.rb +42 -0
  817. data/lib/pubid/un/identifier.rb +40 -0
  818. data/lib/pubid/un/identifiers/document.rb +24 -0
  819. data/lib/pubid/un/identifiers.rb +9 -0
  820. data/lib/pubid/un/parser.rb +25 -0
  821. data/lib/pubid/un/renderer.rb +11 -0
  822. data/lib/pubid/un.rb +46 -0
  823. data/lib/pubid/urn_generator/base.rb +110 -0
  824. data/lib/pubid/urn_parser/base.rb +81 -0
  825. data/lib/pubid/urn_parser/errors.rb +16 -0
  826. data/lib/pubid/urn_parser.rb +14 -0
  827. data/lib/pubid/utils/string_normalizer.rb +196 -0
  828. data/lib/pubid/utils.rb +7 -0
  829. data/lib/pubid/version.rb +3 -1
  830. data/lib/pubid/w3c/builder.rb +55 -0
  831. data/lib/pubid/w3c/identifier.rb +130 -0
  832. data/lib/pubid/w3c/identifiers/candidate_recommendation.rb +31 -0
  833. data/lib/pubid/w3c/identifiers/candidate_recommendation_draft.rb +31 -0
  834. data/lib/pubid/w3c/identifiers/draft_note.rb +31 -0
  835. data/lib/pubid/w3c/identifiers/note.rb +30 -0
  836. data/lib/pubid/w3c/identifiers/obsolete_recommendation.rb +31 -0
  837. data/lib/pubid/w3c/identifiers/proposed_edited_recommendation.rb +31 -0
  838. data/lib/pubid/w3c/identifiers/proposed_recommendation.rb +31 -0
  839. data/lib/pubid/w3c/identifiers/recommendation.rb +31 -0
  840. data/lib/pubid/w3c/identifiers/standard.rb +12 -0
  841. data/lib/pubid/w3c/identifiers/superseded_recommendation.rb +31 -0
  842. data/lib/pubid/w3c/identifiers/working_draft.rb +30 -0
  843. data/lib/pubid/w3c/identifiers.rb +25 -0
  844. data/lib/pubid/w3c/parser.rb +43 -0
  845. data/lib/pubid/w3c/renderer.rb +35 -0
  846. data/lib/pubid/w3c/urn_generator.rb +18 -0
  847. data/lib/pubid/w3c/urn_parser.rb +36 -0
  848. data/lib/pubid/w3c.rb +67 -0
  849. data/lib/pubid/xsf/builder.rb +17 -0
  850. data/lib/pubid/xsf/identifier.rb +66 -0
  851. data/lib/pubid/xsf/identifiers/xep.rb +31 -0
  852. data/lib/pubid/xsf/identifiers.rb +9 -0
  853. data/lib/pubid/xsf/parser.rb +25 -0
  854. data/lib/pubid/xsf/renderer.rb +23 -0
  855. data/lib/pubid/xsf/urn_generator.rb +13 -0
  856. data/lib/pubid/xsf/urn_parser.rb +18 -0
  857. data/lib/pubid/xsf.rb +81 -0
  858. data/lib/pubid.rb +551 -13
  859. data/lib/tasks/docs.rake +37 -0
  860. data/lib/tasks/export.rake +39 -0
  861. data/lib/tasks/website-data.json +7546 -0
  862. metadata +875 -171
  863. data/lib/pubid/registry.rb +0 -30
@@ -0,0 +1,744 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pubid
4
+ module Nist
5
+ # NIST/NBS flavor base class. Canonical name Pubid::Nist::Identifier; every
6
+ # concrete NIST identifier (Identifiers::*) descends from it. Being a real Pubid::Identifier subclass gives
7
+ # native `is_a?` identity and the shared polymorphic `from_hash`.
8
+ class Identifier < ::Pubid::Identifier
9
+ # Delegate to the flavor module so callers can use
10
+ # `Pubid::Nist::Identifier.parse` consistently with other flavors.
11
+ def self.parse(identifier)
12
+ Pubid::Nist.parse(identifier)
13
+ end
14
+
15
+ # Compact, index-friendly serialization (mirrors the key_value flavors
16
+ # ISO/ITU/ETSI, without a 38-field key_value block). Two transforms,
17
+ # applied symmetrically by to_hash/from_hash so the round-trip stays
18
+ # idempotent:
19
+ # - flatten the single-value Code components (series, number) to bare
20
+ # scalars — `value` is the only stored field. NIST's
21
+ # `Components::Code#part` is a *computed* reader
22
+ # (`value.split("-").last`), and prefix/subpart/parts are never
23
+ # assigned on series/number, so the scalar `value` is lossless:
24
+ # expand recomputes exactly what the object would compute anyway;
25
+ # - flatten the plain single-value components (volume) to bare scalars
26
+ # too — `Components::Volume` holds only `value`, so it expands to a
27
+ # bare { "value" => … } with no part;
28
+ # - drop the redundant build artifacts, decomposed pieces of the
29
+ # canonical number that identity/rendering never read.
30
+ COMPACT_FLAT_CODES = %w[series number subseries].freeze
31
+ COMPACT_FLAT_VALUES = %w[volume].freeze
32
+ COMPACT_DROP_ATTRS = %w[first_number second_number].freeze
33
+
34
+ # Deserialize a (possibly compact) hash: expand the flattened scalars
35
+ # back into Code sub-hashes, then let the shared polymorphic from_hash
36
+ # do the real work. Nested `base` documents are expanded recursively by
37
+ # their own from_hash via apply_mappings, so only this level is touched.
38
+ def self.from_hash(data, options = {})
39
+ super(expand_compact_hash(data), options)
40
+ end
41
+
42
+ # Expand a compact hash in place-safe fashion: a scalar series/number
43
+ # becomes { "value" => …, "part" => <last-dash segment> }.
44
+ def self.expand_compact_hash(data)
45
+ return data unless data.is_a?(::Hash)
46
+
47
+ out = data.dup
48
+ COMPACT_FLAT_CODES.each do |key|
49
+ out[key] = expand_code(out[key]) if out[key].is_a?(::String)
50
+ end
51
+ COMPACT_FLAT_VALUES.each do |key|
52
+ out[key] = { "value" => out[key] } if out[key].is_a?(::String)
53
+ end
54
+ out
55
+ end
56
+
57
+ # A flattened Code scalar -> { "value" => …, "part" => <last-dash seg> }.
58
+ def self.expand_code(value)
59
+ code = { "value" => value }
60
+ code["part"] = value.split("-").last if value.include?("-")
61
+ code
62
+ end
63
+
64
+ # Serialize, then apply the compact transforms (recursing into a nested
65
+ # `base`, which lutaml serialized via its own transform — bypassing this
66
+ # override — so it is not compacted otherwise).
67
+ def to_hash(*args)
68
+ hash = super
69
+ compact_hash!(hash) if hash.is_a?(::Hash)
70
+ hash
71
+ end
72
+
73
+ def compact_hash!(hash)
74
+ COMPACT_DROP_ATTRS.each { |key| hash.delete(key) }
75
+ (COMPACT_FLAT_CODES + COMPACT_FLAT_VALUES).each do |key|
76
+ value = hash[key]
77
+ next unless value.is_a?(::Hash) && value.key?("value")
78
+
79
+ hash[key] = value["value"]
80
+ end
81
+ compact_hash!(hash["base"]) if hash["base"].is_a?(::Hash)
82
+ hash
83
+ end
84
+ private :compact_hash!
85
+
86
+ # Default: no typed stages. Subclasses override as needed.
87
+ def self.typed_stages
88
+ []
89
+ end
90
+
91
+ # Generate URN for this identifier
92
+ #
93
+ # @return [String] URN representation
94
+
95
+ # Plain string ("NIST"/"NBS"), not a Components::Publisher wrapper: the
96
+ # value is a single token, so a string serializes flat
97
+ # (`publisher: NBS`, not `publisher: {publisher: NBS}`) and accepts the
98
+ # raw string the circular/supplement builders pass straight through.
99
+ attribute :publisher, :string
100
+ attribute :series, Components::Code # Set by Builder from parsed data
101
+ # SP subseries (Appendix A.2 of the NIST PubID Syntax): for "NIST SP 800-53"
102
+ # the subseries is "800" and the sequence is "53". Populated by the Builder
103
+ # when the series is "SP" and the first number matches a known subseries
104
+ # code. Informational metadata derived from series+number — ignored in
105
+ # equality so a manually-built id (without subseries set) still equals a
106
+ # parsed one.
107
+ attribute :subseries, Components::Code
108
+ attribute :number, Components::Code
109
+
110
+ # V2 COMPONENTS (Lutaml::Model objects) - PROPER SEPARATION
111
+ # `edition` (Components::Edition: type + id + additional_text) is the
112
+ # single source of truth for edition/revision. The former
113
+ # `edition_component` (a byte-identical duplicate) and the `revision`
114
+ # string (always "#{edition.type}#{edition.id}") were unfinished V1->V2
115
+ # migration aliases; both removed. `#revision` survives as a derived
116
+ # reader below.
117
+ attribute :edition, Components::Edition # Edition (type + id): e2, e2021, r5, -3
118
+ attribute :volume, Components::Volume # Volume component (v6)
119
+ attribute :part, Components::Part # Part component (n1 or pt1)
120
+ attribute :stage, Components::Stage
121
+ attribute :version_component, Components::Version
122
+ attribute :update_component, Components::Update
123
+ attribute :translation_component, Components::Translation
124
+ attribute :issue_number, Components::IssueNumber
125
+ attribute :parsed_format, :string # :mr, :short, :long, :abbrev
126
+ # Whether the publisher prefix (NIST/NBS) should be rendered. Defaults
127
+ # to true so the common publisher-bearing id need not serialize the
128
+ # flag at all — the Builder only assigns it (false) for prefix-less
129
+ # inputs, so `to_hash` carries `publisher_was_parsed: false` only in
130
+ # that case and omits it otherwise. (lutaml emits a boolean iff it was
131
+ # explicitly assigned; an omitted key loads as this default.)
132
+ attribute :publisher_was_parsed, :boolean, default: -> { true }
133
+
134
+ # LEGACY attributes (keep for backward compatibility during migration)
135
+ attribute :parts, Components::Code, collection: true
136
+ attribute :revision_year, :string # Year for revision (e.g., r6/1925, r1963, rJun1992)
137
+ attribute :revision_month, :string # Month for revision (e.g., rJun1992)
138
+ attribute :edition_year, :string # Legacy edition year for backward compatibility
139
+ attribute :version, :string
140
+ attribute :update, Components::Update
141
+ attribute :year, :integer
142
+ attribute :month, :integer
143
+
144
+ # Additional attributes for complex patterns
145
+ attribute :first_number, Components::Code
146
+ attribute :second_number, Components::Code
147
+ attribute :update_number, :string
148
+ attribute :update_year, :string
149
+ attribute :addendum, :string
150
+ attribute :addendum_number, :string
151
+ # Single source of truth for the supplement: a structured component with
152
+ # isolated parts (number / year / month / date-range / revision), so a
153
+ # supplement's year is queryable independently of its number. Presence
154
+ # (non-nil) means "is a supplement"; an all-empty component is a bare
155
+ # "sup" marker. Replaces the former flat :supplement string plus the
156
+ # separate date-range/has_revision fields.
157
+ attribute :supplement, Components::Supplement
158
+ attribute :errata, :string
159
+ attribute :index, :string
160
+ attribute :insert, :string
161
+ attribute :section, :string
162
+ attribute :appendix, :string
163
+ attribute :translation, :string
164
+ attribute :draft, :string
165
+ attribute :draft_number, :string # For -draft N → N pd rendering
166
+
167
+ # Default series_code — subclasses override to provide a normalized series name.
168
+ def series_code
169
+ nil
170
+ end
171
+
172
+ def initialize(**attributes)
173
+ # This override calls `super()` with no attributes and assigns through
174
+ # setters instead, so it bypasses the base constructor's coercion and
175
+ # unknown-key check. Apply them here to keep the cross-flavor contract.
176
+ attributes = self.class.normalize_init_attributes(attributes)
177
+ super()
178
+
179
+ attrs = self.class.attributes
180
+ attributes.each do |key, value|
181
+ next if value.nil?
182
+
183
+ setter = :"#{key}="
184
+ public_send(setter, value) if attrs.key?(key)
185
+ end
186
+
187
+ # NOTE: Compound number building is handled by the Builder class
188
+ # Do NOT build compound numbers here - let the builder apply special patterns first
189
+ # See lib/pubid/nist/builder.rb lines 368-472 for compound number logic
190
+ end
191
+
192
+ # Attributes that are build artifacts or rendering aliases, not part
193
+ # of an identifier's logical identity. They diverge between equally-
194
+ # valid spellings of the same id (e.g. long "Rev. 1" vs short "r1"):
195
+ # - first_number/second_number: decomposed parts of the canonical
196
+ # :number, retained from the parse for building
197
+ # - parsed_format: records the input format for round-trip rendering
198
+ # - subseries: derived from series+number (which SP subseries the
199
+ # document belongs to); populated by the Builder for known SP
200
+ # subseries codes. Ignored in equality so a manually-built id
201
+ # without subseries set still equals a parsed one.
202
+ EQUALITY_IGNORED_ATTRS = %i[
203
+ first_number second_number parsed_format subseries
204
+ ].freeze
205
+
206
+ # Logical identity comparison: equal when every attribute except the
207
+ # build artifacts/aliases above matches. (Edition#== already ignores
208
+ # its rendering-only original_prefix.)
209
+ def ==(other)
210
+ return false unless other.instance_of?(self.class)
211
+
212
+ self.class.attributes.each_key.all? do |name|
213
+ EQUALITY_IGNORED_ATTRS.include?(name) || public_send(name) == other.public_send(name)
214
+ end
215
+ end
216
+
217
+ alias eql? ==
218
+
219
+ def hash
220
+ vals = self.class.attributes.each_key.reject do |name|
221
+ EQUALITY_IGNORED_ATTRS.include?(name)
222
+ end.map { |name| public_send(name) }
223
+ [self.class, *vals].hash
224
+ end
225
+
226
+ # Wildcard / partial-identifier match. Treats +self+ as a QUERY pattern
227
+ # and +candidate+ as a concrete document: every ID part SET on the query
228
+ # must equal the candidate's, while parts left unset (nil/empty) are
229
+ # wildcards that match any value. So a query carrying no edition and no
230
+ # supplement matches that document across ALL editions, years, and
231
+ # supplements — the basis for "select docs by ID parts".
232
+ #
233
+ # Asymmetric (unlike ==): "NBS CIRC 25".matches?("NBS CIRC 25sup1924")
234
+ # is true, but not the reverse. The candidate must be the same class or
235
+ # a subclass so series-level identity still holds.
236
+ def matches?(candidate)
237
+ return false unless candidate.is_a?(self.class)
238
+
239
+ self.class.attributes.each_key.all? do |name|
240
+ next true if EQUALITY_IGNORED_ATTRS.include?(name)
241
+
242
+ query_val = public_send(name)
243
+ next true if query_val.nil?
244
+ next true if query_val.is_a?(String) && query_val.empty?
245
+ next true if query_val.is_a?(Array) && query_val.empty?
246
+
247
+ query_val == candidate.public_send(name)
248
+ end
249
+ end
250
+
251
+ # NIST inherits Pubid::Identifier#exclude directly: it now rebuilds via
252
+ # `self.class.new(**attrs)`, so NIST's keyword-only initialize
253
+ # (initialize(**attributes)) works without a local override, and the base
254
+ # version additionally carries the nested-identifier recursion this class's
255
+ # old copy lacked.
256
+
257
+ # Short-form supplement fragment ("sup", "sup1924", "supJan1924",
258
+ # "suprev", " supJun1925-Jun1926"), rendered from the structured
259
+ # component. A present-but-empty component is the bare "sup" marker; a
260
+ # number-less date range gets the leading space the number would have
261
+ # supplied. Shared by base and the per-series to_short_style overrides.
262
+ def supplement_short
263
+ return "" unless supplement
264
+
265
+ prefix = supplement.range? && !number ? " " : ""
266
+ rendered = supplement.to_s(:short)
267
+ prefix + (rendered.empty? ? "sup" : rendered)
268
+ end
269
+
270
+ # Derived, read-only revision string ("r5", "e1979", "-3") for backward
271
+ # compatibility. `edition` is the single stored representation; this is
272
+ # never persisted, compared, or merged — just a convenience view of it.
273
+ # @return [String, nil] revision string (e.g., "r5") or nil
274
+ def revision
275
+ "#{edition.type}#{edition.id}" if edition&.type && edition.id
276
+ end
277
+
278
+ # Backward compatibility: translation method returns translation_component
279
+ # This allows tests to use parsed.translation.language instead of parsed.translation_component.language
280
+ def translation
281
+ translation_component
282
+ end
283
+
284
+ # Backward compatibility: language method returns translation_component
285
+ # This allows tests to use parsed.language instead of parsed.translation_component
286
+ def language
287
+ translation_component
288
+ end
289
+
290
+ # Override parent render to pass NIST-specific format option through
291
+ # to the renderer. Pubid::Identifier#render only forwards
292
+ # :with_edition; NIST needs :nist_format for multi-format support.
293
+ def render(format: :human, **opts)
294
+ registry = self.class.format_registry
295
+ unless registry
296
+ raise ArgumentError, "No format registry configured on #{self.class}"
297
+ end
298
+
299
+ renderer = registry.renderer_for(format)
300
+ unless renderer
301
+ raise ArgumentError, "No renderer registered for format: #{format}"
302
+ end
303
+
304
+ renderer.new(self).render(**opts)
305
+ end
306
+
307
+ # Generate identifier string in specified format
308
+ # @param format [:full, :long, :abbreviated, :short, :mr] output format
309
+ def to_s(format = nil)
310
+ # Handle both keyword argument (hash) and positional argument (symbol/string)
311
+ annotated = format.is_a?(Hash) ? format[:annotated] : nil
312
+ format = format[:format] if format.is_a?(Hash)
313
+
314
+ # Default to parsed_format if available (preserves input format on round-trip)
315
+ # Falls back to :short format for output (normalization)
316
+ # Explicit format parameter always overrides parsed_format
317
+ rendered = render(format: :human,
318
+ nist_format: format || parsed_format&.to_sym || :short)
319
+
320
+ # NIST's `to_s` takes a POSITIONAL format and its `render` override
321
+ # builds no rendering context, so neither the flag nor the context
322
+ # reaches the shared hook. Apply the annotation fallback here.
323
+ annotate_plain_render(rendered, annotated: annotated)
324
+ end
325
+
326
+ # NIST has its own defined MR format (to_mr_style) used by relaton-nist
327
+ # and downstream tooling. The generic Renderers::MrString does not know
328
+ # about NIST series, revisions, supplements, etc., so delegate to the
329
+ # established style for losslessness (issue #142).
330
+ def to_mr_string
331
+ to_mr_style
332
+ end
333
+
334
+ # NIST's MR shape is fixed by the pubid standard and stays uppercase
335
+ # (e.g. `NIST.SP.800-53`). The slug, however, must be lowercase to
336
+ # match the cross-flavor convention; project the MR through `downcase`.
337
+ def to_slug
338
+ to_mr_string.downcase
339
+ end
340
+
341
+ # Returns weight based on amount of defined attributes
342
+ # Used for ranking identifiers by specificity for conflict resolution
343
+ # @return [Integer] weight score (higher = more specific)
344
+ def weight
345
+ self.class.attributes.keys.inject(0) do |sum, key|
346
+ next sum if EQUALITY_IGNORED_ATTRS.include?(key)
347
+
348
+ val = public_send(key)
349
+ val && !val.to_s.empty? ? sum + 1 : sum
350
+ end
351
+ end
352
+
353
+ # Merge another document into this one
354
+ # Used for combining document data, preferring more specific values
355
+ # @param document [Base] another NIST document to merge
356
+ # @return [Base] self with merged attributes
357
+ def merge(document)
358
+ return self unless document.is_a?(Pubid::Nist::Identifier)
359
+
360
+ attrs = self.class.attributes
361
+ attrs.each_key do |var_name|
362
+ next if var_name == :rendering_style
363
+ next if var_name == :parsed_format
364
+
365
+ current_val = public_send(var_name)
366
+ new_val = document.public_send(var_name)
367
+ next unless new_val
368
+
369
+ should_merge = case var_name
370
+ when :publisher, :series, :number
371
+ true
372
+ when :edition
373
+ current_val.nil? || edition_greater?(new_val,
374
+ current_val)
375
+ when :volume, :part, :version
376
+ current_val.nil? || (new_val.to_s.length > current_val.to_s.length)
377
+ when :supplement, :errata, :index, :insert, :section, :appendix, :translation
378
+ true
379
+ when :year, :month, :update, :draft
380
+ true
381
+ else
382
+ false
383
+ end
384
+
385
+ public_send(:"#{var_name}=", new_val) if should_merge
386
+ end
387
+
388
+ self
389
+ end
390
+
391
+ # Helper to compare edition values numerically
392
+ # @return [Boolean] true if edition1 is greater than edition2
393
+ def edition_greater?(edition1, edition2)
394
+ num1 = extract_edition_number(edition1)
395
+ num2 = extract_edition_number(edition2)
396
+ num1 && num2 && num1 > num2
397
+ end
398
+
399
+ # Extract numeric value from edition (r3 -> 3, r5 -> 5, e2 -> 2)
400
+ # @return [Integer, nil] the edition number or nil if not extractable
401
+ def extract_edition_number(edition)
402
+ # Handle both String and Edition component
403
+ edition_str = edition.to_s
404
+ # Match patterns like r3, r5, e2, etc.
405
+ match = edition_str.match(/^[er]?(\d+)$/)
406
+ match ? match[1].to_i : nil
407
+ end
408
+
409
+ public
410
+
411
+ def to_full_style
412
+ # "National Institute of Standards and Technology Special Publication 800-27, Revision A"
413
+ result = publisher_full_name
414
+ result += " #{series_full_name}" if series
415
+ result += " #{number.value}" if number
416
+ result += parts.map { |p| "-#{p}" }.join if parts&.any?
417
+
418
+ # Render volume and issue number in long form: "Vol. 6, No. 12"
419
+ if volume && issue_number
420
+ result += " Vol. #{volume}, #{issue_number.to_s(:long)}"
421
+ elsif volume
422
+ result += " Vol. #{volume}"
423
+ end
424
+
425
+ # NEW: Use edition component properly
426
+ result += " #{edition.to_s(:long)}" if edition
427
+
428
+ result += ", Revision #{revision.sub(/^r/, '')}" if revision
429
+
430
+ # V2: Use version_component
431
+ result += " #{version_component.to_s(:long)}" if version_component
432
+
433
+ # V2: Use update_component
434
+ result += " #{update_component.to_s(:long)}" if update_component
435
+
436
+ # V2: Use stage
437
+ result += " #{stage.to_s(:long)}" if stage
438
+
439
+ # V2: Use translation_component (already includes space)
440
+ result += translation_component.to_s(:long) if translation_component
441
+
442
+ result
443
+ end
444
+
445
+ def to_abbreviated_style
446
+ # "Natl. Inst. Stand. Technol. Spec. Publ. 800-57 Part 1, Revision 4"
447
+ result = publisher_abbreviated_name
448
+ result += " #{series_abbreviated_name}" if series
449
+ result += " #{number}" if number
450
+ result += " Part #{parts.first}" if parts&.any?
451
+
452
+ # NEW: Use edition component properly
453
+ result += " #{edition.to_s(:abbrev)}" if edition
454
+
455
+ result += ", Revision #{revision}" if revision
456
+
457
+ # V2: Use version_component
458
+ result += " #{version_component.to_s(:abbrev)}" if version_component
459
+
460
+ # V2: Use update_component
461
+ result += " #{update_component.to_s(:abbrev)}" if update_component
462
+
463
+ # V2: Use stage
464
+ result += " #{stage.to_s(:abbrev)}" if stage
465
+
466
+ # V2: Use translation_component
467
+ result += ", #{translation_component.to_s(:abbrev)}" if translation_component
468
+
469
+ result
470
+ end
471
+
472
+ def to_short_style
473
+ # "SP 800-187" or "NIST SP 800-187" - handle compound series properly
474
+ result = ""
475
+
476
+ # Determine effective publisher
477
+ # Only show publisher if it was explicitly parsed (either directly or from series prefix)
478
+ effective_publisher = if publisher && publisher_was_parsed
479
+ # Publisher was in input (either as separate field or extracted from "NBS CS" series)
480
+ publisher.to_s
481
+ else
482
+ # No publisher in input, don't show default
483
+ nil
484
+ end
485
+
486
+ # Determine effective series - PREFER series_code if subclass defines it
487
+ # This allows normalization (e.g., LCIRC → LC in LetterCircular)
488
+ effective_series = if series_code
489
+ series_code
490
+ elsif series
491
+ series.to_s
492
+ end
493
+
494
+ # Special handling for compound series that include publisher prefix
495
+ # If series starts with "NBS " (like "NBS CIRC"), use it as-is
496
+ if effective_series&.start_with?("NBS ")
497
+ result += effective_series
498
+ elsif effective_publisher && effective_series
499
+ result += "#{effective_publisher} #{effective_series}"
500
+ elsif effective_series && publisher_was_parsed
501
+ # Only add "NIST" prefix if publisher was explicitly in the input
502
+ result += "NIST #{effective_series}"
503
+ elsif effective_series
504
+ # No publisher in input, just show series without prefix
505
+ result += effective_series
506
+ end
507
+
508
+ result += " #{number}" if number
509
+ result += parts.map { |p| "-#{p}" }.join if parts&.any?
510
+
511
+ # "NIST Research Library (YYYY)" — oddball identifier with no number;
512
+ # the year appears in parens rather than as a date component.
513
+ result += " (#{year})" if year && !number
514
+
515
+ # Append every optional component the parser may have attached
516
+ # (volume, part, edition, version, supplement, update, stage, ...).
517
+ # Shared with the lossy subclasses so they cannot silently drop a
518
+ # distinguishing component and collide with another document.
519
+ result += append_short_components
520
+
521
+ result
522
+ end
523
+
524
+ # Render the optional component "tail" that follows
525
+ # publisher/series/number in short (human) form. Extracted from
526
+ # #to_short_style so subclasses that build a series-specific prefix can
527
+ # reuse it instead of hand-listing components (and forgetting some).
528
+ #
529
+ # skip_part: true lets a series that renders its part differently
530
+ # (e.g. FIPS uses dash "-1", not "pt1") emit the part itself and skip
531
+ # the generic part rendering here, while still getting volume/edition/
532
+ # supplement/etc.
533
+ def append_short_components(skip_part: false)
534
+ result = ""
535
+ effective_part = skip_part ? nil : part
536
+
537
+ # Volume and Part components (v6n1 notation for CSM, pt1 for SP)
538
+ if volume.is_a?(Components::Volume) && effective_part.is_a?(Components::Part)
539
+ # CSM series: v#n# notation
540
+ result += " #{volume}#{effective_part}"
541
+ elsif effective_part.is_a?(Components::Part)
542
+ # SP and other series: use Part.type to determine format
543
+ result += effective_part.to_s
544
+ # Legacy: Render standalone volume (not part of v#n#)
545
+ elsif volume && !issue_number && !effective_part
546
+ vol_str = volume.is_a?(Components::Volume) ? volume.to_s : "v#{volume}"
547
+ result += vol_str
548
+ elsif volume && issue_number
549
+ # Render volume and issue number in short form: "v6n12"
550
+ vol_str = volume.is_a?(Components::Volume) ? volume.to_s : "v#{volume}"
551
+ result += "#{vol_str}n#{issue_number.number}"
552
+ end
553
+
554
+ # Use edition component properly (e2, e2021, r5, -3)
555
+ # NO space before edition when number present (per NIST spec)
556
+ # Only add space for bare edition (no number case) or if original_prefix has specific format
557
+ if edition
558
+ if edition.original_prefix && !edition.original_prefix.empty?
559
+ # original_prefix includes the full prefix (e.g., " Rev. " for verbose format)
560
+ result += edition.to_s
561
+ elsif number
562
+ # Number present, NO space: "800-53r5"
563
+ result += edition.to_s
564
+ else
565
+ # Bare edition, add space: " r5"
566
+ result += " #{edition}"
567
+ end
568
+ end
569
+
570
+ # Use version_component if available, else use version string.
571
+ # Attach directly (no leading space) to match edition rendering
572
+ # (e.g. "800-53r5"), so version reads "800-45ver2" not
573
+ # "800-45 ver2".
574
+ if version_component
575
+ result += version_component.to_s(:short)
576
+ elsif version
577
+ result += "ver#{version}"
578
+ end
579
+
580
+ # Add supplement. NIST/NBS canonical short form is single-p "sup"
581
+ # with the suffix attached directly, no dash (relaton-data-nist
582
+ # uses "sup2", "sup1940", "supA"); date-range keeps its inner dash.
583
+ # Rendered from the structured component; a present-but-empty
584
+ # component is the bare "sup" marker.
585
+ result += supplement_short
586
+
587
+ # Add other attributes
588
+ result += errata.to_s if errata
589
+ result += "index" if index
590
+ result += "insert" if insert
591
+ result += "sec#{section}" if section
592
+ result += "app" if appendix
593
+
594
+ # Add addendum - render as " Add." suffix
595
+ if addendum || addendum_number
596
+ result += " Add."
597
+ end
598
+
599
+ # Use update_component if available, else use update string
600
+ if update_component
601
+ result += update_component.to_s(:short)
602
+ elsif update
603
+ result += "-upd#{update}"
604
+ end
605
+
606
+ # Add draft - render as {N}pd if draft_number present
607
+ if draft_number
608
+ result += " #{draft_number}pd"
609
+ elsif draft&.to_s&.include?("draft") && !draft.to_s.include?("Draft)")
610
+ result += "-draft"
611
+ end
612
+
613
+ # Add stage component (at end, before translation)
614
+ if stage
615
+ result += " #{stage.to_s(:short)}"
616
+ end
617
+
618
+ # Use translation_component if available, else use translation string
619
+ # Note: translation_component.to_s already includes the space prefix
620
+ if translation_component
621
+ result += translation_component.to_s(:short)
622
+ elsif translation
623
+ result += " #{translation}"
624
+ end
625
+
626
+ result
627
+ end
628
+
629
+ def to_mr_style
630
+ # "NIST.SP.800-116r1.ipd" (machine-readable with dots)
631
+ result = (publisher || "NIST").to_s
632
+
633
+ # Determine effective series - PREFER series_code if subclass defines it
634
+ # This allows normalization (e.g., LCIRC → LC in LetterCircular)
635
+ effective_series = if series_code
636
+ series_code
637
+ elsif series
638
+ series.to_s
639
+ end
640
+
641
+ result += ".#{effective_series}" if effective_series
642
+ result += ".#{number}" if number
643
+ result += parts.map { |p| "-#{p}" }.join if parts&.any?
644
+
645
+ result += append_mr_components
646
+
647
+ result
648
+ end
649
+
650
+ # Render the optional component tail for machine-readable (MR) form.
651
+ # Mirrors #append_short_components so the MR output is just as lossless;
652
+ # subclasses that override #to_mr_style reuse this instead of
653
+ # hand-listing components. skip_part: behaves as in the short helper.
654
+ def append_mr_components(skip_part: false)
655
+ result = ""
656
+ effective_part = skip_part ? nil : part
657
+
658
+ # Volume / Part components (pt1, v6n1, etc.)
659
+ if volume.is_a?(Components::Volume) && effective_part.is_a?(Components::Part)
660
+ result += "#{volume}#{effective_part}"
661
+ elsif effective_part.is_a?(Components::Part)
662
+ result += effective_part.to_s
663
+ elsif volume && !issue_number && !effective_part
664
+ result += (volume.is_a?(Components::Volume) ? volume.to_s : "v#{volume}")
665
+ elsif volume && issue_number
666
+ vol_str = volume.is_a?(Components::Volume) ? volume.to_s : "v#{volume}"
667
+ result += "#{vol_str}n#{issue_number.number}"
668
+ end
669
+
670
+ # Use edition component - NO space before edition in MR format (per NIST spec)
671
+ result += edition.to_s if edition
672
+
673
+ # Use version_component
674
+ result += version_component.to_s(:mr) if version_component
675
+
676
+ # Supplement (e.g. ".9981sup7") - keep distinct documents distinct
677
+ result += supplement_short
678
+
679
+ # Use update_component
680
+ result += update_component.to_s(:mr) if update_component
681
+
682
+ # Use stage
683
+ result += ".#{stage.to_s(:mr)}" if stage
684
+
685
+ # Add addendum - render as ".Add." suffix in MR format
686
+ if addendum || addendum_number
687
+ result += ".Add."
688
+ end
689
+
690
+ # Use translation_component
691
+ result += translation_component.to_s(:mr) if translation_component
692
+
693
+ result
694
+ end
695
+
696
+ def series_full_name
697
+ {
698
+ "SP" => "Special Publication",
699
+ "FIPS" => "Federal Information Processing Standards",
700
+ "IR" => "Interagency Report",
701
+ "TN" => "Technical Note",
702
+ }[series] || series
703
+ end
704
+
705
+ def series_abbreviated_name
706
+ {
707
+ "SP" => "Spec. Publ.",
708
+ "FIPS" => "Fed. Inf. Proc. Stand.",
709
+ "IR" => "Interag. Rep.",
710
+ "TN" => "Tech. Note",
711
+ }[series&.to_s || series_code] || (series&.to_s || series_code)
712
+ end
713
+
714
+ def publisher_full_name
715
+ case publisher.to_s
716
+ when "NBS"
717
+ "National Bureau of Standards"
718
+ when "NIST"
719
+ "National Institute of Standards and Technology"
720
+ else
721
+ publisher.to_s
722
+ end
723
+ end
724
+
725
+ def publisher_abbreviated_name
726
+ case publisher.to_s
727
+ when "NBS"
728
+ "Natl. Bur. Stand."
729
+ when "NIST"
730
+ "Natl. Inst. Stand. Technol."
731
+ else
732
+ publisher.to_s
733
+ end
734
+ end
735
+
736
+ # Default publisher for series without explicit publisher
737
+ # Subclasses can override
738
+ def default_publisher
739
+ "NIST"
740
+ end
741
+ end
742
+
743
+ end
744
+ end