asciidoctor-bibliography 0.3.0 → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (73) hide show
  1. checksums.yaml +4 -4
  2. data/README.adoc +23 -4
  3. data/asciidoctor-bibliography.gemspec +8 -8
  4. data/lib/asciidoctor-bibliography.rb +6 -0
  5. data/lib/asciidoctor-bibliography/asciidoctor/bibliographer_preprocessor.rb +35 -23
  6. data/lib/asciidoctor-bibliography/bibliographer.rb +0 -15
  7. data/lib/asciidoctor-bibliography/citation.rb +29 -22
  8. data/lib/asciidoctor-bibliography/databases/bibtex.rb +4 -1
  9. data/lib/asciidoctor-bibliography/formatter.rb +28 -0
  10. data/lib/asciidoctor-bibliography/index.rb +24 -16
  11. data/lib/asciidoctor-bibliography/options.rb +65 -32
  12. data/lib/asciidoctor-bibliography/version.rb +1 -1
  13. data/lib/citeproc/ruby/formats/adoc.rb +36 -0
  14. data/lib/csl/styles/tex-citealp-authoryear.csl +117 -0
  15. data/lib/csl/styles/tex-citealp-numeric.csl +116 -0
  16. data/lib/csl/styles/tex-citealps-authoryear.csl +117 -0
  17. data/lib/csl/styles/tex-citealps-numeric.csl +116 -0
  18. data/lib/csl/styles/tex-citealt-authoryear.csl +119 -0
  19. data/lib/csl/styles/tex-citealt-numeric.csl +119 -0
  20. data/lib/csl/styles/tex-citealts-authoryear.csl +119 -0
  21. data/lib/csl/styles/tex-citealts-numeric.csl +119 -0
  22. data/lib/csl/styles/tex-citeauthor-authoryear.csl +116 -0
  23. data/lib/csl/styles/tex-citeauthor-numeric.csl +116 -0
  24. data/lib/csl/styles/tex-citeauthors-authoryear.csl +116 -0
  25. data/lib/csl/styles/tex-citeauthors-numeric.csl +116 -0
  26. data/lib/csl/styles/tex-citep-authoryear.csl +117 -0
  27. data/lib/csl/styles/tex-citep-numeric.csl +116 -0
  28. data/lib/csl/styles/tex-citeps-authoryear.csl +117 -0
  29. data/lib/csl/styles/tex-citeps-numeric.csl +116 -0
  30. data/lib/csl/styles/tex-citet-authoryear.csl +119 -0
  31. data/lib/csl/styles/tex-citet-numeric.csl +119 -0
  32. data/lib/csl/styles/tex-citets-authoryear.csl +119 -0
  33. data/lib/csl/styles/tex-citets-numeric.csl +119 -0
  34. data/lib/csl/styles/tex-citeyear-authoryear.csl +116 -0
  35. data/lib/csl/styles/tex-citeyear-numeric.csl +116 -0
  36. data/lib/csl/styles/tex-citeyearpar-authoryear.csl +116 -0
  37. data/lib/csl/styles/tex-citeyearpar-numeric.csl +116 -0
  38. data/samples/tex/sample-numbers.adoc +1 -1
  39. data/samples/tex/sample-sort.adoc +1 -1
  40. data/spec/citation_helper.rb +46 -0
  41. data/spec/citation_item_spec.rb +0 -2
  42. data/spec/csl/styles/tex_citealp_authoryear_spec.rb +42 -0
  43. data/spec/csl/styles/tex_citealp_numeric_spec.rb +42 -0
  44. data/spec/csl/styles/tex_citealps_authoryear_spec.rb +42 -0
  45. data/spec/csl/styles/tex_citealps_numeric_spec.rb +42 -0
  46. data/spec/csl/styles/tex_citealt_authoryear_spec.rb +42 -0
  47. data/spec/csl/styles/tex_citealt_numeric_spec.rb +42 -0
  48. data/spec/csl/styles/tex_citealts_authoryear_spec.rb +42 -0
  49. data/spec/csl/styles/tex_citealts_numeric_spec.rb +42 -0
  50. data/spec/csl/styles/tex_citeauthor_authoryear_spec.rb +42 -0
  51. data/spec/csl/styles/tex_citeauthor_numeric_spec.rb +42 -0
  52. data/spec/csl/styles/tex_citeauthors_authoryear_spec.rb +42 -0
  53. data/spec/csl/styles/tex_citeauthors_numeric_spec.rb +42 -0
  54. data/spec/csl/styles/tex_citep_authoryear_spec.rb +42 -0
  55. data/spec/csl/styles/tex_citep_numeric_spec.rb +42 -0
  56. data/spec/csl/styles/tex_citeps_authoryear_spec.rb +42 -0
  57. data/spec/csl/styles/tex_citeps_numeric_spec.rb +42 -0
  58. data/spec/csl/styles/tex_citet_authoryear_spec.rb +42 -0
  59. data/spec/csl/styles/tex_citet_numeric_spec.rb +42 -0
  60. data/spec/csl/styles/tex_citets_authoryear_spec.rb +42 -0
  61. data/spec/csl/styles/tex_citets_numeric_spec.rb +42 -0
  62. data/spec/csl/styles/tex_citeyear_authoryear_spec.rb +42 -0
  63. data/spec/csl/styles/tex_citeyear_numeric_spec.rb +42 -0
  64. data/spec/csl/styles/tex_citeyearpar_authoryear_spec.rb +42 -0
  65. data/spec/csl/styles/tex_citeyearpar_numeric_spec.rb +42 -0
  66. data/spec/database_spec.rb +20 -1
  67. data/spec/macros_spec.rb +21 -0
  68. data/spec/options_spec.rb +105 -1
  69. metadata +72 -24
  70. data/lib/asciidoctor-bibliography/formatters/csl.rb +0 -28
  71. data/lib/asciidoctor-bibliography/formatters/tex.rb +0 -187
  72. data/lib/asciidoctor-bibliography/helpers.rb +0 -41
  73. data/spec/helpers_spec.rb +0 -73
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 60349740c0d584e5373c9f81c67d97a938eb1f87
4
- data.tar.gz: 50fd0f1d8577a54664f9a8e9efdecdb268809edc
3
+ metadata.gz: ec220969b63ad6811daffac07fbf41eaec5a382d
4
+ data.tar.gz: '089f60f0d33c8737b6308b7ab7a494dae7b93803'
5
5
  SHA512:
6
- metadata.gz: cfab5b8627b11ccd161641fc0ff126a30bfc080fbf75e8740aa4341732a205c31992b237f53e67f1d544dbc32f5612a79dfdf717f438c2c966b940f94e3683c2
7
- data.tar.gz: 2f19a9de392c561bf9ad961271b174db27639bdb98ce1c02dcaf1df22f6e2687ae2bd0c4b4311f23018203a6effc4aac96ea4e7ab5b9fd2bafc808d7399d672a
6
+ metadata.gz: 8697d604dd13e6aa72fb652b6e8c61a1bbeef82ab4240d2de96fc0e15d02343646e9494e119baad65269a3802c5b32078e8c233aad864cb707d9943173704d0d
7
+ data.tar.gz: 69704a0dc0dbd0a99142adc00752b904ad5a082baadd755f03b8e49a3b4871e49fdd7fc14bf88011f6eb6e723909791f9b1c986fff1b00e4a5800bb39fcf5964
@@ -16,7 +16,7 @@ Citation styling leverages the popular http://citationstyles.org/[CSL] language
16
16
  so you have direct access to thousands of crowdsourced styles including IEEE,
17
17
  APA, Chicago, DIN and ISO 690.
18
18
 
19
- The `bibliography:[]` command generates a full reference list that adheres to
19
+ The `bibliography::[]` command generates a full reference list that adheres to
20
20
  your configured citation style.
21
21
 
22
22
  On top of that you also have a formatter derived from the `Bib(La)TeX` world,
@@ -28,7 +28,7 @@ Its syntax is designed to be "`native-asciidoctor`":
28
28
  * contextual cite `cite[key, page=3]`;
29
29
  * multiple cites `cite:[key1]+[key2]`;
30
30
  * full cite `fullcite:[key]`; and
31
- * TeX-compatible macros including `citep:[key]`, `citet:[]key` and friends.
31
+ * TeX-compatible macros including `citep:[key]`, `citet:[key]` and friends.
32
32
 
33
33
 
34
34
  == Installation
@@ -180,6 +180,18 @@ or searching through the friendly http://editor.citationstyles.org/[style editor
180
180
  You can also simply use the filename of a CSL file on your machine if you need more customization.
181
181
 
182
182
 
183
+ === Localization
184
+
185
+ Citation styles can be localized using the following option:
186
+
187
+ [source,asciidoc]
188
+ ----
189
+ :bibliography-locale: en-US
190
+ ----
191
+
192
+ The default is `en-US`. Here is an exhaustive list of recognized locales: `af-ZA`, `ar`, `bg-BG`, `ca-AD`, `cs-CZ`, `cy-GB`, `da-DK`, `de-AT`, `de-CH`, `de-DE`, `el-GR`, `en-GB`, `en-US`, `es-CL`, `es-ES`, `es-MX`, `et-EE`, `eu`, `fa-IR`, `fi-FI`, `fr-CA`, `fr-FR`, `he-IL`, `hr-HR`, `hu-HU`, `id-ID`, `is-IS`, `it-IT`, `ja-JP`, `km-KH`, `ko-KR`, `lt-LT`, `lv-LV`, `mn-MN`, `nb-NO`, `nl-NL`, `nn-NO`, `pl-PL`, `pt-BR`, `pt-PT`, `ro-RO`, `ru-RU`, `sk-SK`, `sl-SI`, `sr-RS`, `sv-SE`, `th-TH`, `tr-TR`, `uk-UA`, `vi-VN`, `zh-CN` and `zh-TW`.
193
+
194
+
183
195
  === Hyperlinks
184
196
 
185
197
  By default, citations include hyperlinks to their entry in the bibliography.
@@ -250,7 +262,7 @@ To use them effectively you'll need to know its implementation.
250
262
 
251
263
  This task is not daunting at all, as the http://editor.citationstyles.org/[style editor] allows you to quickly list them and understand their role.
252
264
 
253
- As for the `sort` option, the valid values are `ascending` (default) and `descending` as you'd exect.
265
+ As for the `sort` option, the valid values are `ascending` (default) and `descending` as you'd expect.
254
266
 
255
267
 
256
268
  === TeX-mode
@@ -267,12 +279,17 @@ While the `cite` macro is reserved for CSL styling, all traditional Bib(La)TeX m
267
279
  * `citealp*`
268
280
  * `citeauthor`
269
281
  * `citeauthor*`
270
- * `citeyear` and `citeyearpar`.
282
+ * `citeyear`
283
+ * `citeyearpar`
271
284
 
272
285
  NOTE: no macros are missing since `\cite` is equivalent to `\citet`!
273
286
 
274
287
  To cite multiple items you can concatenate them just like with `cite`.
275
288
 
289
+ All macros accept standard locators, `locator`, `suffix` and `prefix`.
290
+ The behaviour of these parameters is designed to reproduce the one expected
291
+ from the traditional `TeX` citation macros `\cite...[prefix][suffix]{key}`.
292
+
276
293
  You can set their style in the header:
277
294
 
278
295
  [source,asciidoc]
@@ -282,6 +299,8 @@ You can set their style in the header:
282
299
 
283
300
  Accepted values are `authoryear` (default) and `numeric`.
284
301
 
302
+ Furthermore, `fullcite` is also available and accepts no parameters except a single reference key.
303
+
285
304
  == Development
286
305
 
287
306
  We follow Sandi Metz's Rules for this gem, you can read the
@@ -4,7 +4,7 @@ lib = File.expand_path("../lib", __FILE__)
4
4
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
5
  require "asciidoctor-bibliography/version"
6
6
 
7
- Gem::Specification.new do |spec|
7
+ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
8
8
  spec.name = "asciidoctor-bibliography"
9
9
  spec.version = AsciidoctorBibliography::VERSION
10
10
  spec.authors = ["Ribose Inc."]
@@ -19,11 +19,11 @@ Gem::Specification.new do |spec|
19
19
  * contextual cite `cite[key, page=3]`;
20
20
  * multiple cites `cite:[key1]+[key2]`;
21
21
  * full cite `fullcite:[key]`; and
22
- * TeX-compatible macros including `citep:[key]`, `citet:[]key` and friends.
22
+ * TeX-compatible macros including `citep:[key]`, `citet:[key]` and friends.
23
23
 
24
24
  Citation output styles are fully bridged to the CSL library, supporting formats such as IEEE, APA, Chicago, DIN and ISO 690.
25
25
 
26
- The `bibliography:[]` command generates a full reference list that adheres to your configured citation style.
26
+ The `bibliography::[]` command generates a full reference list that adheres to your configured citation style.
27
27
  END
28
28
  spec.homepage = "https://github.com/riboseinc/asciidoctor-bibliography"
29
29
  spec.license = "MIT"
@@ -33,11 +33,11 @@ END
33
33
  spec.test_files = `git ls-files -- {spec}/*`.split("\n")
34
34
  spec.required_ruby_version = Gem::Requirement.new(">= 2.3.0")
35
35
 
36
- spec.add_dependency "asciidoctor"
37
- spec.add_dependency "citeproc-ruby"
38
- spec.add_dependency "csl-styles", "~> 1"
39
- spec.add_dependency "latex-decode", "~> 0.2"
40
- spec.add_dependency "bibtex-ruby"
36
+ spec.add_dependency "asciidoctor", "~> 1.5.6"
37
+ spec.add_dependency "citeproc-ruby", "~> 1.1.7"
38
+ spec.add_dependency "csl-styles", "~> 1.0.1"
39
+ spec.add_dependency "latex-decode", "~> 0.2.2"
40
+ spec.add_dependency "bibtex-ruby", "~> 4.4.4"
41
41
 
42
42
  spec.add_development_dependency "bundler"
43
43
  spec.add_development_dependency "byebug"
@@ -4,3 +4,9 @@ rescue LoadError
4
4
  end
5
5
 
6
6
  require_relative "asciidoctor-bibliography/asciidoctor"
7
+
8
+ module AsciidoctorBibliography
9
+ def self.root
10
+ File.dirname __dir__
11
+ end
12
+ end
@@ -1,6 +1,5 @@
1
1
  require "asciidoctor"
2
2
 
3
- require_relative "../helpers"
4
3
  require_relative "../database"
5
4
  require_relative "../citation"
6
5
  require_relative "../index"
@@ -13,40 +12,53 @@ module AsciidoctorBibliography
13
12
  document.bibliographer.options =
14
13
  ::AsciidoctorBibliography::Options.new_from_reader reader
15
14
 
16
- # Load database(s).
17
- document.bibliographer.database = Database.new(document.bibliographer.options.database)
15
+ document.bibliographer.database =
16
+ ::AsciidoctorBibliography::Database.new document.bibliographer.options.database
18
17
 
19
- # Find, store and replace citations with uuids.
20
- processed_lines = reader.read_lines.map do |line|
21
- line.gsub(Citation::REGEXP) do
22
- citation = Citation.new(*Regexp.last_match.captures)
23
- document.bibliographer.add_citation(citation)
24
- citation.uuid
25
- end
26
- end
18
+ process_reader reader, document.bibliographer
19
+ end
20
+
21
+ private
22
+
23
+ def process_reader(reader, bibliographer)
24
+ # First we fetch citations and replace them with uuids,
25
+ processed_lines = fetch_citations reader.lines, bibliographer
26
+ reader = ::Asciidoctor::Reader.new processed_lines
27
+ # then we render them
28
+ processed_lines = render_citations reader.lines, bibliographer
27
29
  reader = ::Asciidoctor::Reader.new processed_lines
30
+ # and finally we render indices.
31
+ processed_lines = render_indices reader.lines, bibliographer
32
+ ::Asciidoctor::Reader.new processed_lines
33
+ end
34
+
35
+ def fetch_citations(lines, bibliographer)
36
+ lines.join("\n").gsub!(Citation::REGEXP) do
37
+ citation = Citation.new(*Regexp.last_match.captures)
38
+ bibliographer.add_citation(citation)
39
+ citation.uuid
40
+ end.lines.map(&:chomp)
41
+ end
28
42
 
29
- # Find and replace uuids with formatted citations.
30
- processed_lines = reader.lines.join("\n") # for quicker matching
31
- document.bibliographer.citations.each do |citation|
43
+ def render_citations(lines, bibliographer)
44
+ processed_lines = lines.join("\n")
45
+ bibliographer.citations.each do |citation|
32
46
  processed_lines.sub!(citation.uuid) do
33
- citation.render document.bibliographer
47
+ citation.render bibliographer
34
48
  end
35
49
  end
36
- processed_lines = processed_lines.lines.map(&:chomp)
37
- reader = ::Asciidoctor::Reader.new processed_lines
50
+ processed_lines.lines.map(&:chomp)
51
+ end
38
52
 
39
- # Find and format indices.
40
- processed_lines = reader.read_lines.map do |line|
53
+ def render_indices(lines, bibliographer)
54
+ lines.map do |line|
41
55
  if line =~ Index::REGEXP
42
56
  index = Index.new(*Regexp.last_match.captures)
43
- index.render document.bibliographer
57
+ index.render bibliographer
44
58
  else
45
59
  line
46
60
  end
47
- end
48
- processed_lines.flatten!
49
- ::Asciidoctor::Reader.new processed_lines
61
+ end.flatten
50
62
  end
51
63
  end
52
64
  end
@@ -22,20 +22,5 @@ module AsciidoctorBibliography
22
22
  def appearance_index_of(id)
23
23
  @occurring_keys.index(id) + 1
24
24
  end
25
-
26
- def sort
27
- return unless options["order"] == "alphabetical"
28
- @occurring_keys = @occurring_keys.sort_by do |target|
29
- first_author_family_name(target)
30
- end
31
- end
32
-
33
- private
34
-
35
- def first_author_family_name(key)
36
- authors = database.find_entry_by_id(key)["author"]
37
- return "" if authors.nil?
38
- authors.map { |h| h["family"] }.compact.first # TODO: is the first also alphabetically the first?
39
- end
40
25
  end
41
26
  end
@@ -1,11 +1,15 @@
1
1
  require "securerandom"
2
- require_relative "formatters/csl"
3
- require_relative "formatters/tex"
2
+ require_relative "formatter"
4
3
  require_relative "citation_item"
5
4
 
5
+ require "csl/styles"
6
+
6
7
  module AsciidoctorBibliography
7
8
  class Citation
8
- MACRO_NAME_REGEXP = Formatters::TeX::MACROS.keys.concat(%w[cite fullcite]).
9
+ TEX_MACROS = %w[citet citet* citealt citealt* citep citep* citealp citealp*
10
+ citeauthor citeauthor* citeyear citeyearpar].freeze
11
+
12
+ MACRO_NAME_REGEXP = TEX_MACROS.dup.concat(%w[cite fullcite]).
9
13
  map { |s| Regexp.escape s }.join("|").freeze
10
14
  REGEXP = /\\?(#{MACRO_NAME_REGEXP}):(?:(\S*?)?\[(|.*?[^\\])\])(?:\+(\S*?)?\[(|.*?[^\\])\])*/
11
15
  REF_ATTRIBUTES = %i[chapter page section clause].freeze
@@ -31,18 +35,17 @@ module AsciidoctorBibliography
31
35
  render_citation_with_csl(bibliographer)
32
36
  when "fullcite"
33
37
  render_fullcite_with_csl(bibliographer)
34
- when *Formatters::TeX::MACROS.keys
35
- formatter = Formatters::TeX.new(bibliographer.options.tex_style)
36
- formatter.import bibliographer.database
37
- formatter.render bibliographer, self
38
+ when *TEX_MACROS
39
+ filename = ["tex", macro.tr("*", "s"), bibliographer.options.tex_style].join("-")
40
+ filepath = File.join AsciidoctorBibliography.root, "lib/csl/styles", filename
41
+ render_citation_with_csl(bibliographer, style: filepath, tex: true)
38
42
  end
39
43
  end
40
44
 
41
45
  def render_fullcite_with_csl(bibliographer)
42
- formatter = Formatters::CSL.new(bibliographer.options.style)
46
+ formatter = Formatter.new(bibliographer.options.style, locale: bibliographer.options.locale)
43
47
  prepare_fullcite_item bibliographer, formatter
44
48
  formatted_citation = formatter.render(:bibliography, id: citation_items.first.key).join
45
- formatted_citation = Helpers.html_to_asciidoc formatted_citation
46
49
  # We prepend an empty interpolation to avoid interferences w/ standard syntax (e.g. block role is "\n[foo]")
47
50
  "{empty}" + formatted_citation
48
51
  end
@@ -51,9 +54,9 @@ module AsciidoctorBibliography
51
54
  formatter.import([bibliographer.database.find_entry_by_id(citation_items.first.key)])
52
55
  end
53
56
 
54
- def render_citation_with_csl(bibliographer)
55
- formatter = Formatters::CSL.new(bibliographer.options.style)
56
- items = prepare_items bibliographer, formatter
57
+ def render_citation_with_csl(bibliographer, style: bibliographer.options.style, tex: false)
58
+ formatter = Formatter.new(style, locale: bibliographer.options.locale)
59
+ items = prepare_items bibliographer, formatter, tex: tex
57
60
  formatted_citation = formatter.engine.renderer.render(items, formatter.engine.style.citation)
58
61
  escape_brackets_inside_xref! formatted_citation
59
62
  # We prepend an empty interpolation to avoid interferences w/ standard syntax (e.g. block role is "\n[foo]")
@@ -66,25 +69,29 @@ module AsciidoctorBibliography
66
69
  end
67
70
  end
68
71
 
69
- def prepare_items(bibliographer, formatter)
70
- cites_with_local_attributes = citation_items.map { |cite| prepare_metadata bibliographer, cite }
72
+ def prepare_items(bibliographer, formatter, tex: false)
73
+ # NOTE: when we're using our custom TeX CSL styles prefix/suffix are used as
74
+ # varieables for metadata instead of as parameters for citations.
75
+ cites_with_local_attributes = citation_items.map { |cite| prepare_metadata bibliographer, cite, affix: tex }
71
76
  formatter.import cites_with_local_attributes
72
- formatter.sort(mode: :citation)
73
- formatter.data.map(&:cite).each { |item| prepare_item bibliographer.options, item }
77
+ formatter.force_sort!(mode: :citation)
78
+ formatter.data.map(&:cite).each { |item| prepare_item bibliographer.options, item, affix: !tex }
74
79
  end
75
80
 
76
- def prepare_metadata(bibliographer, cite)
81
+ def prepare_metadata(bibliographer, cite, affix: false)
77
82
  bibliographer.database.find_entry_by_id(cite.key).
78
- merge('citation-number': bibliographer.appearance_index_of(cite.key)).
79
- merge('citation-label': cite.key). # TODO: smart label generators
80
- merge('locator': cite.locator.nil? ? nil : " ")
83
+ merge 'citation-number': bibliographer.appearance_index_of(cite.key),
84
+ 'citation-label': cite.key, # TODO: smart label generators
85
+ 'locator': cite.locator.nil? ? nil : " ",
86
+ 'prefix': affix ? cite.prefix : nil,
87
+ 'suffix': affix ? cite.suffix : nil
81
88
  # TODO: why is a non blank 'locator' necessary to display locators set at a later stage?
82
89
  end
83
90
 
84
- def prepare_item(options, item)
91
+ def prepare_item(options, item, affix: true)
85
92
  # TODO: hyperlink, suppress_author and only_author options
86
93
  ci = citation_items.detect { |c| c.key == item.id }
87
- wrap_item item, ci.prefix, ci.suffix
94
+ wrap_item item, ci.prefix, ci.suffix if affix
88
95
  wrap_item item, "xref:#{xref_id(item.id)}{{{", "}}}" if options.hyperlinks?
89
96
  item.label, item.locator = ci.locator
90
97
  end
@@ -17,13 +17,15 @@ module AsciidoctorBibliography
17
17
  ::BibTeX.open(filename, filter: [LatexFilter]).to_citeproc
18
18
  end
19
19
 
20
+ # NOTE: the class below comes from asciidoctor-bibtex
21
+
20
22
  # This filter extends the original latex filter in bibtex-ruby to handle
21
23
  # unknown latex macros more gracefully. We could have used latex-decode
22
24
  # gem together with our custom replacement rules, but latex-decode eats up
23
25
  # all braces after it finishes all decoding. So we hack over the
24
26
  # LaTeX.decode function and insert our rules before `strip_braces`.
25
27
  class LatexFilter < ::BibTeX::Filter
26
- def apply(value)
28
+ def apply(value) # rubocop:disable Metrics/MethodLength; keep this a list, though!
27
29
  text = value.to_s
28
30
  LaTeX::Decode::Base.normalize(text)
29
31
  LaTeX::Decode::Maths.decode!(text)
@@ -32,6 +34,7 @@ module AsciidoctorBibliography
32
34
  LaTeX::Decode::Punctuation.decode!(text)
33
35
  LaTeX::Decode::Symbols.decode!(text)
34
36
  LaTeX::Decode::Greek.decode!(text)
37
+ # TODO: could we be doing something smarter with some macros, e.g. \url?
35
38
  text.gsub!(/\\url\{(.+?)\}/, ' \\1 ')
36
39
  text.gsub!(/\\\w+(?=\s+\w)/, "")
37
40
  text.gsub!(/\\\w+(?:\[.+?\])?\s*\{(.+?)\}/, '\\1')
@@ -0,0 +1,28 @@
1
+ require "citeproc"
2
+ require "csl/styles"
3
+ require "yaml"
4
+
5
+ require_relative "../citeproc/ruby/formats/adoc"
6
+
7
+ module AsciidoctorBibliography
8
+ class Formatter < ::CiteProc::Processor
9
+ def initialize(style, locale: "en-US")
10
+ super style: style, format: :adoc, locale: locale
11
+ end
12
+
13
+ def replace_bibliography_sort(array)
14
+ new_keys = array.map(&::CSL::Style::Sort::Key.method(:new))
15
+ new_sort = ::CSL::Style::Sort.new.add_children(*new_keys)
16
+
17
+ bibliography = engine.style.find_child("bibliography")
18
+ bibliography.find_child("sort")&.unlink
19
+
20
+ bibliography.add_child new_sort
21
+ end
22
+
23
+ def force_sort!(mode:)
24
+ # Valid modes are :citation and :bibliography
25
+ engine.sort! data, engine.style.send(mode).sort_keys if engine.style.send(mode).sort?
26
+ end
27
+ end
28
+ end
@@ -1,7 +1,5 @@
1
1
  require "asciidoctor/attribute_list"
2
- require_relative "formatters/csl"
3
-
4
- require_relative "helpers"
2
+ require_relative "formatter"
5
3
 
6
4
  module AsciidoctorBibliography
7
5
  class Index
@@ -16,23 +14,13 @@ module AsciidoctorBibliography
16
14
  end
17
15
 
18
16
  def render(bibliographer)
19
- formatter = Formatters::CSL.new(bibliographer.options.style)
20
-
21
- unless bibliographer.options.sort.nil?
22
- formatter.replace_bibliography_sort bibliographer.options.sort
23
- end
24
-
25
- filtered_db = bibliographer.occurring_keys.
26
- map { |id| bibliographer.database.find_entry_by_id(id) }.
27
- map { |entry| prepare_entry_metadata bibliographer, entry }
28
- formatter.import filtered_db
29
- formatter.sort(mode: :bibliography)
17
+ formatter = setup_formatter bibliographer
30
18
 
31
19
  lines = []
32
20
  formatter.bibliography.each_with_index do |reference, index|
33
21
  line = "{empty}"
34
22
  line << "anchor:#{anchor_id(formatter.data[index].id)}[]"
35
- line << Helpers.html_to_asciidoc(reference)
23
+ line << reference
36
24
  lines << line
37
25
  end
38
26
 
@@ -40,6 +28,26 @@ module AsciidoctorBibliography
40
28
  lines.join("\n\n").lines.map(&:strip)
41
29
  end
42
30
 
31
+ private
32
+
33
+ def setup_formatter(bibliographer)
34
+ formatter = Formatter.new(bibliographer.options.style, locale: bibliographer.options.locale)
35
+
36
+ formatter.replace_bibliography_sort bibliographer.options.sort unless bibliographer.options.sort.nil?
37
+
38
+ filtered_db = prepare_filtered_db bibliographer
39
+ formatter.import filtered_db
40
+ formatter.force_sort!(mode: :bibliography)
41
+
42
+ formatter
43
+ end
44
+
45
+ def prepare_filtered_db(bibliographer)
46
+ bibliographer.occurring_keys.
47
+ map { |id| bibliographer.database.find_entry_by_id(id) }.
48
+ map { |entry| prepare_entry_metadata bibliographer, entry }
49
+ end
50
+
43
51
  def prepare_entry_metadata(bibliographer, entry)
44
52
  entry.
45
53
  merge('citation-number': bibliographer.appearance_index_of(entry["id"])).
@@ -51,7 +59,7 @@ module AsciidoctorBibliography
51
59
  end
52
60
 
53
61
  def render_entry_label(target, formatter)
54
- Helpers.html_to_asciidoc formatter.render(:bibliography, id: target).join
62
+ formatter.render(:bibliography, id: target).join
55
63
  end
56
64
 
57
65
  def render_entry(target, formatter)