pubid 2.0.0.pre.alpha.49 → 2.0.0.pre.alpha.50
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.
- checksums.yaml +4 -4
- data/data/parg/iso.json +8510 -1
- data/data/parg/nist.json +9588 -1
- data/lib/pubid/iso/builder.rb +9 -0
- data/lib/pubid/iso/parser.rb +14 -1
- data/lib/pubid/nist/builder.rb +10 -0
- data/lib/pubid/nist/caster.rb +6 -0
- data/lib/pubid/nist/parser.rb +17 -1
- data/lib/pubid/nist/series/base.rb +15 -1
- data/lib/pubid/version.rb +1 -1
- data/lib/tasks/api_reference.rake +86 -0
- metadata +2 -1
data/lib/pubid/iso/builder.rb
CHANGED
|
@@ -32,6 +32,15 @@ module Pubid
|
|
|
32
32
|
return Identifiers::TcDocument
|
|
33
33
|
end
|
|
34
34
|
|
|
35
|
+
# Bare TC reference (pubid-iso#285): "184/SC 4/WG 12 N10291" — the
|
|
36
|
+
# ISO/TC route without the ORIGINATOR prefix. tc_type is absent by
|
|
37
|
+
# construction; sc_type is the route's required segment and cannot
|
|
38
|
+
# appear on a standard identifier.
|
|
39
|
+
if parsed_hash[:sc_type] && parsed_hash[:tc_number]
|
|
40
|
+
parsed_hash[:tc_type] = "TC"
|
|
41
|
+
return Identifiers::TcDocument
|
|
42
|
+
end
|
|
43
|
+
|
|
35
44
|
# An explicit document type (e.g. from a URN's `:tr:`/`:ts:` token) pins
|
|
36
45
|
# the class regardless of the stage. The stage and type are separate URN
|
|
37
46
|
# fields, but the stage is later folded into `:type_with_stage` (e.g.
|
data/lib/pubid/iso/parser.rb
CHANGED
|
@@ -29,7 +29,8 @@ module Pubid
|
|
|
29
29
|
# TC documents must come first since they start with "ISO/"
|
|
30
30
|
# and we need to distinguish them from regular ISO/IEC identifiers
|
|
31
31
|
rule(:identifier) do
|
|
32
|
-
|
|
32
|
+
bare_tc_document |
|
|
33
|
+
nsb_iso_identifier |
|
|
33
34
|
tc_document |
|
|
34
35
|
directives_identifiers |
|
|
35
36
|
jcgm_identifier |
|
|
@@ -62,6 +63,18 @@ module Pubid
|
|
|
62
63
|
(str(":") >> year_digits.as(:year)).maybe
|
|
63
64
|
end
|
|
64
65
|
|
|
66
|
+
# Bare TC document reference (pubid-iso#285): "184/SC 4/WG 12 N10291"
|
|
67
|
+
# — the ISO/TC route without the ORIGINATOR prefix; the builder
|
|
68
|
+
# canonicalizes the publisher to ISO. The SC segment is required so
|
|
69
|
+
# bare numbers cannot leak into the route.
|
|
70
|
+
rule(:bare_tc_document) do
|
|
71
|
+
digits.as(:tc_number) >>
|
|
72
|
+
str("/") >> sc_type >> space >> digits.as(:sc_number) >>
|
|
73
|
+
(str("/") >> wg_type >> space >> digits.as(:wg_number)).maybe >>
|
|
74
|
+
space >> str("N") >> space? >> digits.as(:number) >>
|
|
75
|
+
(str(":") >> year_digits.as(:year)).maybe
|
|
76
|
+
end
|
|
77
|
+
|
|
65
78
|
rule(:tc_subcommittee_part) do
|
|
66
79
|
# Full path: TC/SC 4/WG 3
|
|
67
80
|
(str("/") >> sc_type >> space >> digits.as(:sc_number) >> str("/") >>
|
data/lib/pubid/nist/builder.rb
CHANGED
|
@@ -104,6 +104,16 @@ module Pubid
|
|
|
104
104
|
identifier.part = letter_suffix_part
|
|
105
105
|
end
|
|
106
106
|
|
|
107
|
+
# Part type "n" with a letter value — "NCSTAR 1nA" (pubid#555):
|
|
108
|
+
# the corpus rows carry part {type: "n", value: <letter>}, which
|
|
109
|
+
# renders as "n<letter>".
|
|
110
|
+
if parsed_hash[:n_letter_part]
|
|
111
|
+
identifier.part = Components::Part.new(
|
|
112
|
+
type: "n",
|
|
113
|
+
value: parsed_hash[:n_letter_part].to_s.sub(/\An/, "").upcase,
|
|
114
|
+
)
|
|
115
|
+
end
|
|
116
|
+
|
|
107
117
|
# NEW: If we extracted an Edition from edition_dash_year, assign it now
|
|
108
118
|
if edition_from_dash_year
|
|
109
119
|
identifier.edition = edition_from_dash_year
|
data/lib/pubid/nist/caster.rb
CHANGED
|
@@ -729,6 +729,12 @@ module Pubid
|
|
|
729
729
|
str_value = value.to_s.strip
|
|
730
730
|
return nil if str_value.empty?
|
|
731
731
|
|
|
732
|
+
# The index suffix parses from both spellings ("index", "indx");
|
|
733
|
+
# the component's value is the long form either way, so
|
|
734
|
+
# parse(render(x)) == x for the CRPL-F-B corpus rows that print
|
|
735
|
+
# "indx" (pubid#557).
|
|
736
|
+
str_value = "index" if type == :index
|
|
737
|
+
|
|
732
738
|
# For volume, create Volume component from string value
|
|
733
739
|
# This handles patterns like "v1" that come from parser as simple strings
|
|
734
740
|
if type == :volume
|
data/lib/pubid/nist/parser.rb
CHANGED
|
@@ -139,10 +139,18 @@ module Pubid
|
|
|
139
139
|
# Single letter: any letter not followed by excluded keywords
|
|
140
140
|
rule(:number_suffix) do
|
|
141
141
|
(str("U") >> lower_letter) |
|
|
142
|
+
# n+UPPERCASE annex suffix (e.g., 1nA, 85nB — the BH/HR/NCSTAR/SP
|
|
143
|
+
# annex designations, pubid#555). Before the general letter branch,
|
|
144
|
+
# which would consume the lone "n" and strand the capital letter.
|
|
145
|
+
(str("n") >> upper_letter) |
|
|
142
146
|
# An "r" directly followed by a digit is the revision marker (pubid#170),
|
|
143
147
|
# not a suffix — leave it for the second_number/edition rules.
|
|
144
148
|
# The guard sits before the letter so it tests the suffix start itself.
|
|
145
|
-
((str("r") >> digit).absent? >> match("[a-zA-Z]") >>
|
|
149
|
+
((str("r") >> digit).absent? >> match("[a-zA-Z]") >>
|
|
150
|
+
# An uppercase letter following the suffix letter is the part
|
|
151
|
+
# type "n" + letter form ("1nA", pubid#555) — the suffix must
|
|
152
|
+
# stop so the parts rule can take the whole token.
|
|
153
|
+
match("[A-Z]").absent? >> (
|
|
146
154
|
# Match suffixes
|
|
147
155
|
str("ec") |
|
|
148
156
|
str("ndex") |
|
|
@@ -438,9 +446,13 @@ module Pubid
|
|
|
438
446
|
# Dash with letter suffix (e.g., 1-1A, 1-3B for NCSTAR, 73-197Ur for IR)
|
|
439
447
|
# Must come before GCR pattern which expects another dash
|
|
440
448
|
# Supports U+lowercase letter suffix (e.g., Ur, Ua, Ub-Uj for Unclassified variants)
|
|
449
|
+
# Supports n+UPPERCASE annex suffix (e.g., 1-1nA, 1-1nB — the BH/HR/NCSTAR
|
|
450
|
+
# annex designations, pubid#555): the n prefix lowercases to the same
|
|
451
|
+
# letter_suffix face as the plain letter
|
|
441
452
|
# For other uppercase letters, only match single letter (A, B, C) to avoid consuming revision r
|
|
442
453
|
(dash >> digits.as(:letter_base) >> (
|
|
443
454
|
(str("U") >> lower_letter.as(:letter_suffix_extra)) |
|
|
455
|
+
(str("n") >> upper_letter.as(:letter_suffix_extra)) |
|
|
444
456
|
upper_letter
|
|
445
457
|
).as(:letter_suffix)).as(:letter_number) |
|
|
446
458
|
# Dash-SEPARATED letter suffix on a numbered part (e.g., 21-4-B,
|
|
@@ -669,6 +681,10 @@ module Pubid
|
|
|
669
681
|
# Put more specific patterns first
|
|
670
682
|
# CRITICAL: new_stage BEFORE language_code to avoid "ipd" being treated as translation
|
|
671
683
|
new_stage |
|
|
684
|
+
# Part type "n" with a letter value — "NCSTAR 1nA" (pubid#555):
|
|
685
|
+
# the letter part suffixes the corpus renders as n<A> (Part
|
|
686
|
+
# type "n"); must precede the generic index/letter rules.
|
|
687
|
+
(str("n") >> upper_letter).as(:n_letter_part) |
|
|
672
688
|
section | index | insert | appendix | pd_suffix |
|
|
673
689
|
edition | date | legacy_edition | revision |
|
|
674
690
|
version | # MOVED BEFORE volume - try dotted versions (v1.1) before simple volumes (v1)
|
|
@@ -16,6 +16,16 @@ module Pubid
|
|
|
16
16
|
# Return a cast hash, or nil to skip assignment.
|
|
17
17
|
# Default: split letter suffix into a Part component.
|
|
18
18
|
def self.cast_letter_number(value, _parsed_hash)
|
|
19
|
+
# The n+UPPERCASE annex capture (pubid#555, e.g., 800-85nB) arrives
|
|
20
|
+
# as a nested letter_suffix_extra: it casts to the n-notation Part
|
|
21
|
+
# (Part.new(type: "n", value: "B") renders "nB").
|
|
22
|
+
if value[:letter_suffix].is_a?(Hash)
|
|
23
|
+
letter = value[:letter_suffix][:letter_suffix_extra].to_s
|
|
24
|
+
return nil if letter.empty?
|
|
25
|
+
|
|
26
|
+
return { part: Components::Part.new(type: "n", value: letter.upcase) }
|
|
27
|
+
end
|
|
28
|
+
|
|
19
29
|
full = combine_letter_suffix(value)
|
|
20
30
|
return nil if full.nil? || full.empty?
|
|
21
31
|
|
|
@@ -47,8 +57,12 @@ module Pubid
|
|
|
47
57
|
def self.finalize_identifier(_identifier, _parsed_hash); end
|
|
48
58
|
|
|
49
59
|
# Combine `:letter_suffix` and `:letter_suffix_extra` (e.g., "U" + "r").
|
|
60
|
+
# The n+UPPERCASE annex capture nests the extra inside the suffix hash
|
|
61
|
+
# (pubid#555): unwrap it before stringifying.
|
|
50
62
|
def self.combine_letter_suffix(value)
|
|
51
|
-
suffix = value[:letter_suffix]
|
|
63
|
+
suffix = value[:letter_suffix]
|
|
64
|
+
suffix = suffix[:letter_suffix_extra] if suffix.is_a?(Hash)
|
|
65
|
+
suffix = suffix.to_s.strip
|
|
52
66
|
extra = value[:letter_suffix_extra].to_s.strip
|
|
53
67
|
extra.empty? ? suffix : "#{suffix}#{extra}"
|
|
54
68
|
end
|
data/lib/pubid/version.rb
CHANGED
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "yard"
|
|
4
|
+
|
|
5
|
+
namespace :docs do
|
|
6
|
+
# Generates docs/api-reference.md from the YARD registry over lib/ —
|
|
7
|
+
# the generated API reference the website assembles (pubid#577). CI
|
|
8
|
+
# regenerates and fails on drift, so the committed file cannot rot.
|
|
9
|
+
desc "Generate docs/api-reference.md from YARD"
|
|
10
|
+
task :api_reference do
|
|
11
|
+
require "pubid"
|
|
12
|
+
Pubid.eager_load_flavors!
|
|
13
|
+
YARD::Registry.clear
|
|
14
|
+
YARD::Parser::SourceParser.parse(Dir.glob("lib/**/*.rb").sort, [])
|
|
15
|
+
|
|
16
|
+
entry = lambda do |obj|
|
|
17
|
+
sig = obj.signature.to_s.strip.sub(/\Adef\s+/, "").gsub(/\s+/, " ")
|
|
18
|
+
doc = obj.docstring.strip.lines.first.to_s.strip
|
|
19
|
+
out = +"### `#{sig}`\n"
|
|
20
|
+
out << "\n#{doc}\n" unless doc.empty?
|
|
21
|
+
out
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
module_section = lambda do |path, names|
|
|
25
|
+
mod = YARD::Registry.at(path)
|
|
26
|
+
return "" unless mod
|
|
27
|
+
|
|
28
|
+
out = +"## `#{path}`\n\n"
|
|
29
|
+
names.sort.each do |name|
|
|
30
|
+
obj = mod.child("::#{name}") || mod.child(name.to_s)
|
|
31
|
+
out << entry.call(obj) if obj
|
|
32
|
+
end
|
|
33
|
+
out
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
out = +<<~HEADER
|
|
37
|
+
# API reference
|
|
38
|
+
|
|
39
|
+
<!-- Generated by `rake docs:api_reference` (YARD over lib/) — do not
|
|
40
|
+
edit by hand; CI fails on drift. The website assembles this file
|
|
41
|
+
into the library reference. -->
|
|
42
|
+
|
|
43
|
+
HEADER
|
|
44
|
+
|
|
45
|
+
out << module_section.call(
|
|
46
|
+
"Pubid",
|
|
47
|
+
%w[parse from_hash locate_stage locate_stage_flavors prefixes
|
|
48
|
+
prefix_flavors parse_by_prefix],
|
|
49
|
+
)
|
|
50
|
+
errors = YARD::Registry.at("Pubid::Errors")
|
|
51
|
+
if errors
|
|
52
|
+
out << "## `Pubid::Errors`\n\n"
|
|
53
|
+
errors.children
|
|
54
|
+
.select { |c| c.is_a?(YARD::CodeObjects::ClassObject) }
|
|
55
|
+
.sort_by(&:name).each do |klass|
|
|
56
|
+
sig = "Pubid::Errors::#{klass.name}"
|
|
57
|
+
sup = klass.superclass.to_s.split("::").last
|
|
58
|
+
doc = klass.docstring.strip.lines.first.to_s.strip
|
|
59
|
+
out << "### `#{sig} < #{sup}`\n"
|
|
60
|
+
out << "\n#{doc}\n" unless doc.empty?
|
|
61
|
+
end
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
Pubid::Registry.flavor_names.sort.each do |flavor|
|
|
65
|
+
mod = Pubid::Registry.get(flavor)
|
|
66
|
+
names = %w[parse parse_urn locate_stage locate_stage_by_harmonized_code
|
|
67
|
+
locate_type prefixes all_typed_stages all_project_stages]
|
|
68
|
+
.select { |m| mod.respond_to?(m) }
|
|
69
|
+
out << module_section.call(mod.name, names)
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
id_klass = YARD::Registry.at("Pubid::Identifier")
|
|
73
|
+
if id_klass
|
|
74
|
+
out << "## `Pubid::Identifier` (instance methods)\n\n"
|
|
75
|
+
id_klass.meths(scope: :instance, inherited: false)
|
|
76
|
+
.select { |m| m.visibility == :public }
|
|
77
|
+
.sort_by(&:name).each do |obj|
|
|
78
|
+
out << entry.call(obj)
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
File.write("docs/api-reference.md", out)
|
|
83
|
+
puts "docs/api-reference.md: #{out.lines.count} lines, " \
|
|
84
|
+
"#{Pubid::Registry.flavor_names.size} flavors"
|
|
85
|
+
end
|
|
86
|
+
end
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: pubid
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 2.0.0.pre.alpha.
|
|
4
|
+
version: 2.0.0.pre.alpha.50
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Ribose Inc.
|
|
@@ -1048,6 +1048,7 @@ files:
|
|
|
1048
1048
|
- lib/pubid/xsf/renderer.rb
|
|
1049
1049
|
- lib/pubid/xsf/urn_generator.rb
|
|
1050
1050
|
- lib/pubid/xsf/urn_parser.rb
|
|
1051
|
+
- lib/tasks/api_reference.rake
|
|
1051
1052
|
- lib/tasks/benchmark.rake
|
|
1052
1053
|
- lib/tasks/conformance.rake
|
|
1053
1054
|
- lib/tasks/docs.rake
|