relaton-un 0.2.0 → 0.2.1

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 015c42748ac36cf87b341555c5b951fc1cf4afb86ed7308bad2172358c6480f0
4
- data.tar.gz: b4c0f18281564885142a4b5b1f3b019fab1633681927817e7b1575d6888b420d
3
+ metadata.gz: a0fcd871844a8cafc3b613fc6e77ccd219717122b95bfdfafca8362b46f63490
4
+ data.tar.gz: 952d86d121183c5a32e822a2f7bb3ae651851f87999dfe21ccf0bb0b302fbf5f
5
5
  SHA512:
6
- metadata.gz: 2d63b262ab2ddfb66ac9a698cd705835a7e2ea04b40f38d55d657843bb8d41a8ef3e32256692c7fd05f177b8ffb2c12cb51047f94bea81743504a605bc599186
7
- data.tar.gz: a061b39e0a51c7bd210096e7c615e48140db1e704565c256c04c9e9ae3601ebe8860a0a65d494db1b9c9622245a6114c2a4aa59510be5101a4cf671e40bbfb21
6
+ metadata.gz: 03c2ccfe9ce6cce797f2a5c905b74976793c8245ed36b813dfaf55e3989e1cdb41426a6d52a357c71cffa42d67427d78ae6c4d3418fdf471b176276557ff2579
7
+ data.tar.gz: 9f2c4b1db54d38a5e48407a33d01aab3d2e98c8d6eec700262f33f00505d7a2339378a5511ba600cad13a01ee710c5e4ba1e6ef703282644f4febe46b660fad0
data/grammars/un.rng CHANGED
@@ -107,7 +107,9 @@
107
107
  <zeroOrMore>
108
108
  <ref name="submissionlanguage"/>
109
109
  </zeroOrMore>
110
- <ref name="editorialgroup"/>
110
+ <optional>
111
+ <ref name="editorialgroup"/>
112
+ </optional>
111
113
  <zeroOrMore>
112
114
  <ref name="ics"/>
113
115
  </zeroOrMore>
@@ -0,0 +1,25 @@
1
+ module RelatonUn
2
+ class EditorialGroup
3
+ include RelatonBib
4
+
5
+ # @return [Array<String>]
6
+ attr_reader :committee
7
+
8
+ # @param committee [Array<String>]
9
+ def initialize(committee)
10
+ @committee = committee
11
+ end
12
+
13
+ # @param builder [Nokogiri::XML::Builder]
14
+ def to_xml(builder)
15
+ builder.editorialgroup do |b|
16
+ committee.each { |c| b.committee c }
17
+ end
18
+ end
19
+
20
+ # @return [Array<Hash>, Hash]
21
+ def to_hash
22
+ single_element_array(committee.map { |c| { "committee" => c } })
23
+ end
24
+ end
25
+ end
@@ -1,5 +1,33 @@
1
1
  module RelatonUn
2
- class HashConverter < RelatonBib::HashConverter
2
+ class HashConverter < RelatonIsoBib::HashConverter
3
+ class << self
4
+ # @override RelatonIsoBib::HashConverter.hash_to_bib
5
+ # @param args [Hash]
6
+ # @param nested [TrueClass, FalseClass]
7
+ # @return [Hash]
8
+ def hash_to_bib(args, nested = false)
9
+ ret = super
10
+ return if ret.nil?
3
11
 
12
+ session_hash_to_bib ret
13
+ ret
14
+ end
15
+
16
+ private
17
+
18
+ # @param ret [Hash]
19
+ def session_hash_to_bib(ret)
20
+ ret[:session] = Session.new(ret[:session]) if ret[:session]
21
+ end
22
+
23
+ # @param ret [Hash]
24
+ def editorialgroup_hash_to_bib(ret)
25
+ eg = ret[:editorialgroup]
26
+ return unless eg
27
+
28
+ committee = eg.map { |e| e[:committee] }
29
+ ret[:editorialgroup] = EditorialGroup.new array(committee)
30
+ end
31
+ end
4
32
  end
5
33
  end
@@ -3,6 +3,51 @@
3
3
  module RelatonUn
4
4
  # Hit.
5
5
  class Hit < RelatonBib::Hit
6
+ # rubocop:disable Layout/LineLength
7
+
8
+ # There is distribution PRO (A/47/PV.102/CORR.1, A/47/PV.54)
9
+ BODY = {
10
+ "A" => "General Assembly",
11
+ "E" => "Economic and Social Council",
12
+ "S" => "Security Council",
13
+ "T" => "Trusteeship Council",
14
+ "ACC" => "Administrative Committee on Coordination",
15
+ "AT" => "United Nations Administrative Tribunal",
16
+ "CAT" => "Committee against Torture",
17
+ "CCPR" => "Human Rights Committee",
18
+ "CD" => "Conference on Disarmament",
19
+ "CEDAW" => "Committee on the Elimination of All Forms of Discrimination against Women",
20
+ "CERD" => "Committee on the Elimination of Racial Discrimination",
21
+ "CRC" => "Committee on the Rights of the Child",
22
+ "DC" => "Disarmament Commission",
23
+ "DP" => "United Nations Development Programme",
24
+ "HS" => "United Nations Centre for Human Settlements (HABITAT)",
25
+ "TD" => "United Nations Conference on Trade and Development",
26
+ "UNEP" => "United Nations Environment Programme",
27
+ "TRADE" => "Committee on Trade",
28
+ "CEFACT" => "Centre for Trade Facilitation and Electronic Business",
29
+ "C.1" => "Disarmament and International Security Committee",
30
+ "C.2" => "Economic and Financial Committee",
31
+ "C.3" => "Social, Humanitarian & Cultural Issues",
32
+ "C.4" => "Special Political and Decolonization Committee",
33
+ "C.5" => "Administrative and Budgetary Committee",
34
+ "C.6" => "Sixth Committee (Legal)",
35
+ "PC" => "Preparatory Committee",
36
+ "AEC" => "Atomic Energy Commission",
37
+ "AGRI" => "Committee on Agriculture",
38
+ "AMCEN" => "African Ministerial Conference on the Environment",
39
+ "AMCOW" => "African Ministers’ Council on Water",
40
+ "ECA" => "Economic Commission for Africa",
41
+ "ESCAP" => "Economic and Social Commission for Asia and Pacific",
42
+ "ECE" => "Economic Commission for Europe",
43
+ "ECWA" => "Economic Commission for Western Asia",
44
+ "UNFF" => "United Nations Forum on Forests",
45
+ "ENERGY" => "Committee on Sustainable Energy",
46
+ "FAO" => "Food and Agriculture Organization",
47
+ "UNCTAD" => "United Nations Conference on Trade and Development",
48
+ }.freeze
49
+ # rubocop:enable Layout/LineLength
50
+
6
51
  # Parse page.
7
52
  # @return [RelatonUn::UnBibliographicItem]
8
53
  def fetch
@@ -11,48 +56,90 @@ module RelatonUn
11
56
 
12
57
  private
13
58
 
59
+ # rubocop:disable Metrics/MethodLength
60
+
61
+ # @return [RelatonUn::UnBibliographicItem]
14
62
  def un_bib_item
15
63
  UnBibliographicItem.new(
16
64
  type: "standard",
17
65
  fetched: Date.today.to_s,
18
- docid: docid,
66
+ docid: fetch_docid,
19
67
  docnumber: hit[:ref],
20
68
  language: ["en"],
21
69
  script: ["Latn"],
22
- title: title,
23
- date: date,
24
- link: link,
25
- keyword: keyword
70
+ title: fetch_title,
71
+ date: fetch_date,
72
+ link: fetch_link,
73
+ keyword: fetch_keyword,
74
+ session: fetch_session,
75
+ distribution: fetch_distribution,
76
+ editorialgroup: fetch_editorialgroup,
26
77
  )
27
78
  end
79
+ # rubocop:enable Metrics/MethodLength
28
80
 
29
81
  # @return [Array<RelatonBib::DocumentIdentifier>]
30
- def docid
31
- [RelatonBib::DocumentIdentifier.new(id: hit[:ref], type: "UN")]
82
+ def fetch_docid
83
+ hit[:symbol].map do |s|
84
+ RelatonBib::DocumentIdentifier.new(id: s, type: "UN")
85
+ end
32
86
  end
33
87
 
34
88
  # @return [Array<RelatonBib::TypedTitleString>]
35
- def title
36
- fs = RelatonBib::FormattedString.new(content: hit[:title], language: "en", script: "Latn")
37
- [RelatonBib::TypedTitleString.new(type: "main", title: fs)]
89
+ def fetch_title
90
+ # fs = RelatonBib::FormattedString.new(
91
+ # content: hit[:title], language: "en", script: "Latn",
92
+ # )
93
+ # [RelatonBib::TypedTitleString.new(type: "main", title: fs)]
94
+ [{ title_main: hit[:title], language: "en", script: "Latn" }]
38
95
  end
39
96
 
40
97
  # @return [Array<RelatonBib::BibliographicDate>]
41
- def date
98
+ def fetch_date
42
99
  d = []
43
- d << RelatonBib::BibliographicDate.new(type: "published", on: hit[:date_pub]) if hit[:date_pub]
44
- d << RelatonBib::BibliographicDate.new(type: "issued", on: hit[:date_rel]) if hit[:date_rel]
100
+ d << bibdate("published", hit[:date_pub]) if hit[:date_pub]
101
+ d << bibdate("issued", hit[:date_rel]) if hit[:date_rel]
45
102
  d
46
103
  end
47
104
 
105
+ # @param type [String]
106
+ # @param on [String]
107
+ # @return [RelatonBib::BibliographicDate]
108
+ def bibdate(type, on)
109
+ RelatonBib::BibliographicDate.new type: type, on: on
110
+ end
111
+
48
112
  # @return [Array<RelatonBib::TypedUri>]
49
- def link
113
+ def fetch_link
50
114
  hit[:link].map { |l| RelatonBib::TypedUri.new l }
51
115
  end
52
116
 
53
117
  # @return [Array<String>]
54
- def keyword
118
+ def fetch_keyword
55
119
  hit[:keyword].split(", ")
56
120
  end
121
+
122
+ # @return [RelatonUn::Session]
123
+ def fetch_session
124
+ Session.new(session_number: hit[:session], agenda_id: hit[:agenda])
125
+ end
126
+
127
+ # @return [String]
128
+ def fetch_distribution
129
+ UnBibliographicItem::DISTRIBUTIONS[hit[:distribution]]
130
+ end
131
+
132
+ # @return [RelatonUn::EditorialGroup, NilClass]
133
+ def fetch_editorialgroup
134
+ tc = hit[:ref].match(/^[\S]+/).to_s.split(/\/|-/).reduce([]) do |m, v|
135
+ if BODY[v] then m << BODY[v]
136
+ elsif v =~ /(AC|C|CN|CONF|GC|SC|Sub|WG).\d+|PC/ then m << v
137
+ else m
138
+ end
139
+ end.uniq
140
+ return unless tc.any?
141
+
142
+ RelatonUn::EditorialGroup.new tc
143
+ end
57
144
  end
58
145
  end
@@ -6,7 +6,8 @@ require "http-cookie"
6
6
  module RelatonUn
7
7
  # Page of hit collection.
8
8
  class HitCollection < RelatonBib::HitCollection
9
- AGENT = "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36"
9
+ AGENT = "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_3) "\
10
+ "AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36"
10
11
  DOMAIN = "https://documents.un.org"
11
12
  BOUNDARY = "----WebKitFormBoundary6hkaBvITDck8dHCn"
12
13
 
@@ -17,52 +18,10 @@ module RelatonUn
17
18
  @jar = HTTP::CookieJar.new
18
19
  @http = Net::HTTP.new @uri.host, @uri.port
19
20
  @http.use_ssl = true
21
+ @http.read_timeout = 120
20
22
  if (form_resp = get_page)
21
- form = Nokogiri::HTML form_resp.body
22
- form_data = form.xpath(
23
- "//input[@type!='radio']",
24
- "//input[@type='radio'][@checked]",
25
- "//select[@name!='view:_id1:_id2:cbLang']",
26
- "//textarea"
27
- ).reduce([]) do |m, i|
28
- v = case i[:name]
29
- when "view:_id1:_id2:txtSymbol" then text
30
- when "view:_id1:_id2:cbType" then "FP"
31
- when "view:_id1:_id2:cbSort" then "R"
32
- when "$$xspsubmitid" then "view:_id1:_id2:_id130"
33
- when "$$xspsubmitscroll" then "0|167"
34
- else i[:value]
35
- end
36
- m << %{--#{BOUNDARY}}
37
- m << %{Content-Disposition: form-data; name="#{i[:name]}"\r\n\r\n#{v}}
38
- end
39
- form_data << %{--#{BOUNDARY}--\r\n}
40
- req = Net::HTTP::Post.new form.at("//form")[:action]
41
- set_headers req
42
- req["Content-Type"] = "multipart/form-data, boundary=#{BOUNDARY}"
43
- req.body = form_data.join("\r\n")
44
- resp = @http.request req
45
- page_resp = get_page URI.parse(resp["location"]).request_uri
46
- doc = Nokogiri::HTML page_resp.body
47
- @array = doc.css("div.viewHover").map do |item|
48
- ref = item.at("div/div/a")&.text&.sub "\u00A0", ""
49
- title = item.at("div/div/span")&.text
50
- keyword = item.at("div[3]/div[5]/span")&.text
51
- date_pub = item.at("//label[.='Publication Date: ']/following-sibling::span")&.text
52
- en = item.at("//span[.='ENGLISH']/../..")
53
- date_rel = en.at("./following-sibling::span[contains(@id, 'cfRelDateE')]").text
54
- link = en.xpath("//a[contains(@title, 'Open')]").map do |l|
55
- { content: l[:href], type: l[:title].match(/PDF|Word/).to_s.downcase }
56
- end
57
- Hit.new({
58
- ref: ref,
59
- title: title,
60
- keyword: keyword,
61
- date_pub: date_pub,
62
- date_rel: date_rel,
63
- link: link
64
- }, self)
65
- end
23
+ doc = Nokogiri::HTML page_resp(form_resp, text).body
24
+ @array = doc.css("div.viewHover").map { |item| hit item }
66
25
  end
67
26
  end
68
27
 
@@ -84,9 +43,125 @@ module RelatonUn
84
43
  get_page request_uri, deep + 1
85
44
  end
86
45
 
46
+ # rubocop:disable Metrics/MethodLength
47
+
48
+ # @param form [Nokogiri::HTML::Document]
49
+ # @param text [String]
50
+ # @return [Array<String>]
51
+ def form_data(form, text)
52
+ fd = form.xpath(
53
+ "//input[@type!='radio']",
54
+ "//input[@type='radio'][@checked]",
55
+ "//select[@name!='view:_id1:_id2:cbLang']",
56
+ "//textarea",
57
+ ).reduce([]) do |m, i|
58
+ v = case i[:name]
59
+ when "view:_id1:_id2:txtSymbol" then text
60
+ when "view:_id1:_id2:cbType" then "FP"
61
+ when "view:_id1:_id2:cbSort" then "R"
62
+ when "$$xspsubmitid" then "view:_id1:_id2:_id130"
63
+ when "$$xspsubmitscroll" then "0|167"
64
+ else i[:value]
65
+ end
66
+ m << %{--#{BOUNDARY}}
67
+ m << %{Content-Disposition: form-data; name="#{i[:name]}"\r\n\r\n#{v}}
68
+ end
69
+ fd << %{--#{BOUNDARY}--\r\n}
70
+ end
71
+ # rubocop:enable Metrics/MethodLength
72
+
73
+ # @param form_resp [Net::HTTPOK]
74
+ # @param text [String]
75
+ # @return [Net::HTTPOK]
76
+ def page_resp(form_resp, text)
77
+ form = Nokogiri::HTML form_resp.body
78
+ req = Net::HTTP::Post.new form.at("//form")[:action]
79
+ set_headers req
80
+ req["Content-Type"] = "multipart/form-data, boundary=#{BOUNDARY}"
81
+ req.body = form_data(form, text).join("\r\n")
82
+ resp = @http.request req
83
+ get_page URI.parse(resp["location"]).request_uri
84
+ end
85
+
86
+ # @param item [Nokogiri::XML::Element]
87
+ # @return [RelatonUn::Hit]
88
+ def hit(item)
89
+ Hit.new(hit_data(item), self)
90
+ end
91
+
92
+ # @param item [Nokogiri::XML::Element]
93
+ # @return [Hash]
94
+ def hit_data(item)
95
+ en = item.at("//span[.='ENGLISH']/../..")
96
+ {
97
+ ref: item.at("div/div/a")&.text&.sub("\u00A0", ""),
98
+ symbol: symbol(item),
99
+ title: item.at("div/div/span")&.text,
100
+ keyword: item.at("div[3]/div[5]/span")&.text,
101
+ date_pub: date_pub(item),
102
+ date_rel: date_rel(en),
103
+ link: link(en),
104
+ session: session(item),
105
+ agenda: agenda(item),
106
+ distribution: distribution(item)
107
+ }
108
+ end
109
+
110
+ # @param item [Nokogiri::XML::Element]
111
+ # @return [String]
112
+ def symbol(item)
113
+ item.xpath("div/div[not(contains(@class, 'hidden'))]/"\
114
+ "label[contains(.,'Symbol')]/following-sibling::span[1]").map &:text
115
+ end
116
+
117
+ # @param item [Nokogiri::XML::Element]
118
+ # @return [String]
119
+ def date_pub(item)
120
+ item.at("//label[.='Publication Date: ']/following-sibling::span")&.text
121
+ end
122
+
123
+ # @param item [Nokogiri::XML::Element]
124
+ # @return [String]
125
+ def date_rel(item)
126
+ item.at("./following-sibling::span[contains(@id, 'cfRelDateE')]")&.text
127
+ end
128
+
129
+ # @param item [Nokogiri::XML::Element]
130
+ # @return [Array<Hash>]
131
+ def link(item)
132
+ item.xpath("//a[contains(@title, 'Open')]").map do |l|
133
+ {
134
+ content: l[:href],
135
+ type: l[:title].match(/PDF|Word/).to_s.downcase,
136
+ }
137
+ end
138
+ end
139
+
140
+ # @param item [Nokogiri::XML::Element]
141
+ # @return [String]
142
+ def session(item)
143
+ item.at("//label[.='Session / Year:']/following-sibling::span")&.text
144
+ end
145
+
146
+ # @param item [Nokogiri::XML::Element]
147
+ # @return [String]
148
+ def agenda(item)
149
+ item.at("//label[.='Agenda Item(s):']/following-sibling::span")&.text
150
+ end
151
+
152
+ # @param item [Nokogiri::XML::Element]
153
+ # @return [String]
154
+ def distribution(item)
155
+ item.at("//label[.='Distribution:']/following-sibling::span")&.text
156
+ end
157
+
158
+ # rubocop:disable Metrics/MethodLength
159
+
160
+ # @param req [Net::HTTP::Get, Net::HTTP::Post]
87
161
  def set_headers(req)
88
162
  set_cookie req
89
- req["Accept"] = "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9"
163
+ req["Accept"] = "text/html,application/xhtml+xml,application/xml;q=0.9,"\
164
+ "image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9"
90
165
  req["Accept-Encoding"] = "gzip, deflate, br"
91
166
  req["Cache-Control"] = "max-age=0"
92
167
  req["Connection"] = "keep-alive"
@@ -98,7 +173,9 @@ module RelatonUn
98
173
  req["Upgrade-Insecure-Requests"] = "1"
99
174
  req["User-Agent"] = AGENT
100
175
  end
176
+ # rubocop:enable Metrics/MethodLength
101
177
 
178
+ # @param req [Net::HTTP::Get, Net::HTTP::Post]
102
179
  def set_cookie(req)
103
180
  req["Cookie"] = HTTP::Cookie.cookie_value @jar.cookies(@uri)
104
181
  end
@@ -0,0 +1,65 @@
1
+ module RelatonUn
2
+ class Session
3
+ include RelatonBib
4
+
5
+ # @return [String, NilClass]
6
+ attr_reader :session_number, :collaboration, :agenda_id, :item_footnote
7
+
8
+ # @return [Date, NilClass]
9
+ attr_reader :session_date
10
+
11
+ # @return [Array<String>]
12
+ attr_reader :item_number, :item_name, :subitem_name
13
+
14
+ # @param session_number [String]
15
+ # @param session_date [String]
16
+ # @param item_number [Array<String>]
17
+ # @pqrqm item_name [Array<String>]
18
+ # @pqrqm subitem_name [Array<String>]
19
+ # @param collaboration [String]
20
+ # @param agenda_id [String]
21
+ # @param item_footnote [String]
22
+ def initialize(**args)
23
+ @session_number = args[:session_number]
24
+ @session_date = Date.parse args[:session_date] if args[:session_date]
25
+ @item_number = args.fetch(:item_number, [])
26
+ @item_name = args.fetch(:item_name, [])
27
+ @subitem_name = args.fetch(:subitem_name, [])
28
+ @collaboration = args[:collaboration]
29
+ @agenda_id = args[:agenda_id]
30
+ @item_footnote = args[:item_footnote]
31
+ end
32
+
33
+ # rubocop:disable Metrics/AbcSize
34
+
35
+ # @param [Nokogiri::XML::Builder]
36
+ def to_xml(builder)
37
+ builder.session do |b|
38
+ b.number session_number if session_number
39
+ b.send "session-date", session_date.to_s if session_date
40
+ item_number.each { |n| b.send "item-number", n }
41
+ item_name.each { |n| b.send "item-name", n }
42
+ subitem_name.each { |n| b.send "subitem-name", n }
43
+ b.collaboration collaboration if collaboration
44
+ b.send "agenda-id", agenda_id if agenda_id
45
+ b.send "item-footnote", item_footnote if item_footnote
46
+ end
47
+ end
48
+
49
+ # rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
50
+ # @return [Hash]
51
+ def to_hash
52
+ hash = {}
53
+ hash["session_number"] = session_number if session_number
54
+ hash["session_date"] = session_date.to_s if session_date
55
+ hash["item_number"] = single_element_array(item_number) if item_number.any?
56
+ hash["item_name"] = single_element_array(item_name) if item_name.any?
57
+ hash["subitem_name"] = single_element_array(subitem_name) if subitem_name.any?
58
+ hash["collaboration"] = collaboration if collaboration
59
+ hash["agenda_id"] = agenda_id if agenda_id
60
+ hash["item_footnote"] = item_footnote if item_footnote
61
+ hash
62
+ end
63
+ # rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
64
+ end
65
+ end
@@ -1,8 +1,44 @@
1
1
  module RelatonUn
2
- class UnBibliographicItem < RelatonBib::BibliographicItem
2
+ class UnBibliographicItem < RelatonIsoBib::IsoBibliographicItem
3
3
  TYPES = %w[
4
4
  recommendation plenary addendum communication corrigendum reissue agenda
5
5
  budgetary sec-gen-notes expert-report resolution
6
6
  ].freeze
7
+
8
+ DISTRIBUTIONS = { "GEN" => "general", "LTD" => "limited",
9
+ "DER" => "restricted" }.freeze
10
+
11
+ # @return [RelatonUn::Session, NilClass]
12
+ attr_reader :session
13
+
14
+ # @return [String, NilClass]
15
+ attr_reader :distribution
16
+
17
+ # @param session [RelatonUn::Session, NilClass]
18
+ # @param distribution [String]
19
+ def initialize(**args)
20
+ if args[:distribution] && !DISTRIBUTIONS.has_value?(args[:distribution])
21
+ warn "[relaton-un] WARNING: invalid distribution: #{args[:distribution]}"
22
+ end
23
+ @distribution = args.delete :distribution
24
+ @session = args.delete :session
25
+ super **args
26
+ end
27
+
28
+ # @param builder [Nokogiri::XML::Builder]
29
+ # @param bibdata [TrueClasss, FalseClass, NilClass]
30
+ def to_xml(builder = nil, **opts)
31
+ super(builder, **opts) do |b|
32
+ b.distribution distribution if distribution
33
+ session&.to_xml b if session
34
+ end
35
+ end
36
+
37
+ # @return [Hash]
38
+ def to_hash
39
+ hash = super
40
+ hash["session"] = session.to_hash if session
41
+ hash
42
+ end
7
43
  end
8
44
  end
@@ -9,9 +9,11 @@ module RelatonUn
9
9
  def search(text)
10
10
  HitCollection.new text
11
11
  rescue SocketError, Errno::EINVAL, Errno::ECONNRESET, EOFError,
12
- Net::HTTPBadResponse, Net::HTTPHeaderSyntaxError, Net::ProtocolError,
13
- OpenSSL::SSL::SSLError, Errno::ETIMEDOUT
14
- raise RelatonBib::RequestError, "Could not access #{HitCollection::DOMAIN}"
12
+ Net::HTTPBadResponse, Net::HTTPHeaderSyntaxError,
13
+ Net::ProtocolError, Net::ReadTimeout, OpenSSL::SSL::SSLError,
14
+ Errno::ETIMEDOUT => e
15
+ raise RelatonBib::RequestError,
16
+ "Could not access #{HitCollection::DOMAIN}: #{e.message}"
15
17
  end
16
18
 
17
19
  # @param ref [String] document reference
@@ -23,7 +25,8 @@ module RelatonUn
23
25
  /^(UN\s)?(?<code>.*)/ =~ ref
24
26
  result = isobib_search_filter(code)
25
27
  if result
26
- warn "[relaton-un] (\"#{ref}\") found #{result.fetch.docidentifier.first.id}"
28
+ warn "[relaton-un] (\"#{ref}\") "\
29
+ "found #{result.fetch.docidentifier[0].id}"
27
30
  result.fetch
28
31
  end
29
32
  end
@@ -36,7 +39,7 @@ module RelatonUn
36
39
  # @return [RelatonUn::HitCollection]
37
40
  def isobib_search_filter(code)
38
41
  result = search(code)
39
- result.select { |i| i.hit[:ref] == code }.first
42
+ result.select { |i| i.hit[:symbol].include? code }.first
40
43
  end
41
44
  end
42
45
  end
@@ -1,3 +1,3 @@
1
1
  module RelatonUn
2
- VERSION = "0.2.0".freeze
2
+ VERSION = "0.2.1".freeze
3
3
  end
@@ -1,16 +1,61 @@
1
1
  module RelatonUn
2
- class XMLParser < RelatonBib::XMLParser
2
+ class XMLParser < RelatonIsoBib::XMLParser
3
3
  class << self
4
+ # @param xml [String]
5
+ # @return [RelatonUn::UnBibliographicItem, NilClass]
4
6
  def from_xml(xml)
5
7
  doc = Nokogiri::XML xml
6
8
  doc.remove_namespaces!
7
- titem = doc.at("/bibitem|/bibdata")
8
- if titem
9
- UnBibliographicItem.new(item_data(titem))
9
+ item = doc.at("/bibitem|/bibdata")
10
+ if item
11
+ UnBibliographicItem.new(item_data(item))
10
12
  else
11
- warn "[relaton-un] can't find bibitem or bibdata element in the XML"
13
+ warn "[relaton-un] WARNING: can't find bibitem or bibdata element in"\
14
+ " the XML"
12
15
  end
13
16
  end
17
+
18
+ private
19
+
20
+ # @param item [Nokogiri::XML::Element]
21
+ # @return [Hash]
22
+ def item_data(item)
23
+ data = super
24
+ data[:session] = fetch_session item
25
+ data[:distribution] = item.at("distribution")&.text
26
+ data
27
+ end
28
+
29
+ # rubocop:disable Metrics/AbcSize, Metrics/MethodLength
30
+
31
+ # @param item [Nokogiri::XML::Element]
32
+ # @return [RelatonUn::Session]
33
+ def fetch_session(item)
34
+ session = item.at "./ext/session"
35
+ return unless session
36
+
37
+ RelatonUn::Session.new(
38
+ session_number: session.at("number")&.text,
39
+ session_date: session.at("session-date")&.text,
40
+ item_number: session.xpath("item-number").map(&:text),
41
+ item_name: session.xpath("item-name").map(&:text),
42
+ subitem_name: session.xpath("subitem-name").map(&:text),
43
+ collaboration: session.at("collaboration")&.text,
44
+ agenda_id: session.at("agenda-id")&.text,
45
+ item_footnote: session.at("item-footnote")&.text,
46
+ )
47
+ end
48
+ # rubocop:enable Metrics/AbcSize, Metrics/MethodLength
49
+
50
+ # @param ext [Nokogiri::XML::Element]
51
+ # @return [RelatonUn::EditorialGroup]
52
+ def fetch_editorialgroup(ext)
53
+ eg = ext.at("./editorialgroup")
54
+ return unless eg
55
+
56
+ committee = eg&.xpath("committee")&.map &:text
57
+ EditorialGroup.new committee
58
+ end
14
59
  end
15
60
  end
16
61
  end
data/lib/relaton_un.rb CHANGED
@@ -1,4 +1,4 @@
1
- require "relaton_bib"
1
+ require "relaton_iso_bib"
2
2
  require "relaton_un/version"
3
3
  require "relaton_un/un_bibliographic_item"
4
4
  require "relaton_un/un_bibliography"
@@ -6,6 +6,8 @@ require "relaton_un/hit_collection"
6
6
  require "relaton_un/hit"
7
7
  require "relaton_un/hash_converter"
8
8
  require "relaton_un/xml_parser"
9
+ require "relaton_un/session"
10
+ require "relaton_un/editorialgroup"
9
11
 
10
12
  module RelatonUn
11
13
  class Error < StandardError; end
data/relaton_un.gemspec CHANGED
@@ -1,31 +1,32 @@
1
1
  lib = File.expand_path("lib", __dir__)
2
2
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
3
- require 'relaton_un/version'
3
+ require "relaton_un/version"
4
4
 
5
+ # rubocop:disable Metrics/BlockLength
5
6
  Gem::Specification.new do |spec|
6
7
  spec.name = "relaton-un"
7
8
  spec.version = RelatonUn::VERSION
8
9
  spec.authors = ["Ribose Inc."]
9
10
  spec.email = ["open.source@ribose.com"]
10
11
 
11
- spec.summary = "RelatonIso: retrieve CC Standards for bibliographic use "\
12
- "using the IsoBibliographicItem model"
13
- spec.description = "RelatonIso: retrieve CC Standards for bibliographic use "\
14
- "using the IsoBibliographicItem model"
12
+ spec.summary = "RelatonIso: retrieve CC Standards for bibliographic "\
13
+ "use using the IsoBibliographicItem model"
14
+ spec.description = "RelatonIso: retrieve CC Standards for bibliographic "\
15
+ "use using the IsoBibliographicItem model"
15
16
  spec.homepage = "https://github.com/relaton/relaton-un"
16
17
  spec.license = "BSD-2-Clause"
17
18
  spec.required_ruby_version = Gem::Requirement.new(">= 2.4.0")
18
19
 
19
- # spec.metadata["allowed_push_host"] = "TODO: Set to 'http://mygemserver.com'"
20
-
21
20
  spec.metadata["homepage_uri"] = spec.homepage
22
- # spec.metadata["source_code_uri"] = "TODO: Put your gem's public repo URL here."
21
+ spec.metadata["source_code_uri"] = spec.homepage
23
22
  # spec.metadata["changelog_uri"] = "TODO: Put your gem's CHANGELOG.md URL here."
24
23
 
25
24
  # Specify which files should be added to the gem when it is released.
26
25
  # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
27
- spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
28
- `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
26
+ spec.files = Dir.chdir(File.expand_path(__dir__)) do
27
+ `git ls-files -z`.split("\x0").reject do |f|
28
+ f.match(%r{^(test|spec|features)/})
29
+ end
29
30
  end
30
31
  spec.bindir = "exe"
31
32
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
@@ -42,6 +43,7 @@ Gem::Specification.new do |spec|
42
43
 
43
44
  spec.add_dependency "faraday"
44
45
  spec.add_dependency "http-cookie"
45
- spec.add_dependency "relaton-bib", "~> 0.9.0"
46
+ spec.add_dependency "relaton-iso-bib", ">= 0.9.2"
46
47
  spec.add_dependency "unf_ext", ">= 0.0.7.7"
47
48
  end
49
+ # rubocop:enable Metrics/BlockLength
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: relaton-un
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.2.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-03-30 00:00:00.000000000 Z
11
+ date: 2020-04-19 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: debase
@@ -151,19 +151,19 @@ dependencies:
151
151
  - !ruby/object:Gem::Version
152
152
  version: '0'
153
153
  - !ruby/object:Gem::Dependency
154
- name: relaton-bib
154
+ name: relaton-iso-bib
155
155
  requirement: !ruby/object:Gem::Requirement
156
156
  requirements:
157
- - - "~>"
157
+ - - ">="
158
158
  - !ruby/object:Gem::Version
159
- version: 0.9.0
159
+ version: 0.9.2
160
160
  type: :runtime
161
161
  prerelease: false
162
162
  version_requirements: !ruby/object:Gem::Requirement
163
163
  requirements:
164
- - - "~>"
164
+ - - ">="
165
165
  - !ruby/object:Gem::Version
166
- version: 0.9.0
166
+ version: 0.9.2
167
167
  - !ruby/object:Gem::Dependency
168
168
  name: unf_ext
169
169
  requirement: !ruby/object:Gem::Requirement
@@ -205,10 +205,12 @@ files:
205
205
  - grammars/reqt.rng
206
206
  - grammars/un.rng
207
207
  - lib/relaton_un.rb
208
+ - lib/relaton_un/editorialgroup.rb
208
209
  - lib/relaton_un/hash_converter.rb
209
210
  - lib/relaton_un/hit.rb
210
211
  - lib/relaton_un/hit_collection.rb
211
212
  - lib/relaton_un/processor.rb
213
+ - lib/relaton_un/session.rb
212
214
  - lib/relaton_un/un_bibliographic_item.rb
213
215
  - lib/relaton_un/un_bibliography.rb
214
216
  - lib/relaton_un/version.rb
@@ -220,6 +222,7 @@ licenses:
220
222
  - BSD-2-Clause
221
223
  metadata:
222
224
  homepage_uri: https://github.com/relaton/relaton-un
225
+ source_code_uri: https://github.com/relaton/relaton-un
223
226
  post_install_message:
224
227
  rdoc_options: []
225
228
  require_paths: