texlive[72157] Master: citation-style-language (1sep24)

commits+karl at tug.org commits+karl at tug.org
Sun Sep 1 22:46:03 CEST 2024


Revision: 72157
          https://tug.org/svn/texlive?view=revision&revision=72157
Author:   karl
Date:     2024-09-01 22:46:02 +0200 (Sun, 01 Sep 2024)
Log Message:
-----------
citation-style-language (1sep24)

Modified Paths:
--------------
    trunk/Master/texmf-dist/doc/latex/citation-style-language/CHANGELOG.md
    trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.pdf
    trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.tex
    trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.1
    trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.man1.pdf
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-bibtex-data.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-engine.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-latex-parser.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-manager.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-node-citation.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-util.lua
    trunk/Master/texmf-dist/scripts/citation-style-language/citeproc.lua
    trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-cite.sty
    trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-compatible.sty
    trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language.sty
    trunk/Master/texmf-dist/tex/latex/citation-style-language/styles/apa.csl
    trunk/Master/tlpkg/tlpsrc/citation-style-language.tlpsrc

Modified: trunk/Master/texmf-dist/doc/latex/citation-style-language/CHANGELOG.md
===================================================================
--- trunk/Master/texmf-dist/doc/latex/citation-style-language/CHANGELOG.md	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/doc/latex/citation-style-language/CHANGELOG.md	2024-09-01 20:46:02 UTC (rev 72157)
@@ -7,6 +7,16 @@
 
 ## [Unreleased]
 
+## [0.6.3] - 2024-08-28
+
+### Added
+
+- Add support for citation affixes.
+
+### Fixed
+
+- Fix `\ref` with underscore in citation affixes ([#74](https://github.com/zepinglee/citeproc-lua/issues/74)).
+
 ## [0.6.2] - 2024-08-21
 
 ### Added
@@ -15,7 +25,7 @@
 
 ### Fixed
 
-- Fix note position in multiple chapters ([#72](https://github.com/zepinglee/citeproc-lua/discussions/72)).
+- Fix note position in multiple chapters ([#72](https://github.com/zepinglee/citeproc-lua/issues/72)).
 - Fix incorrect locale map of UKenglish.
 
 ## [0.6.1] - 2024-08-15
@@ -22,7 +32,7 @@
 
 ### Fixed
 
-- Fix parsing quotation marks ([#71](https://github.com/zepinglee/citeproc-lua/discussions/71)).
+- Fix parsing quotation marks ([#71](https://github.com/zepinglee/citeproc-lua/issues/71)).
 
 ## [0.6.0] - 2024-07-31
 
@@ -231,7 +241,8 @@
 
 - Initial CTAN release.
 
-[Unreleased]: https://github.com/zepinglee/citeproc-lua/compare/v0.6.2...HEAD
+[Unreleased]: https://github.com/zepinglee/citeproc-lua/compare/v0.6.3...HEAD
+[0.6.3]: https://github.com/zepinglee/citeproc-lua/compare/v0.6.2...v0.6.3
 [0.6.2]: https://github.com/zepinglee/citeproc-lua/compare/v0.6.1...v0.6.2
 [0.6.1]: https://github.com/zepinglee/citeproc-lua/compare/v0.6.0...v0.6.1
 [0.6.0]: https://github.com/zepinglee/citeproc-lua/compare/v0.5.1...v0.6.0

Modified: trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.pdf
===================================================================
(Binary files differ)

Modified: trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.tex
===================================================================
--- trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.tex	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/doc/latex/citation-style-language/citation-style-language-doc.tex	2024-09-01 20:46:02 UTC (rev 72157)
@@ -51,7 +51,7 @@
   }%
 }
 
-\date{2024-08-21 v0.6.2}
+\date{2024-08-28 v0.6.3}
 
 \maketitle
 

Modified: trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.1
===================================================================
--- trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.1	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.1	2024-09-01 20:46:02 UTC (rev 72157)
@@ -1,4 +1,4 @@
-.TH citeproc-lua 1 "0.6.2"
+.TH citeproc-lua 1 "0.6.3"
 .SH NAME
 citeproc-lua \- make CSL citations and bibliography for LaTeX
 .SH SYNOPSIS

Modified: trunk/Master/texmf-dist/doc/man/man1/citeproc-lua.man1.pdf
===================================================================
(Binary files differ)

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-bibtex-data.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-bibtex-data.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-bibtex-data.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -4205,6 +4205,11 @@
       csl = nil,
       source = "adrbirthday.bst",
     },
+    citations = {
+      csl = nil,
+      source = "publist.dbx",
+      type = "literal",
+    },
   },
   macros = {
     acmcs = {

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-engine.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-engine.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-engine.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -53,10 +53,21 @@
 --- at alias ItemId string | number
 --- at alias NoteIndex integer
 --- at alias ChapterIndex number
---- at alias CitationData {citationID: CitationId, citationItems: CitationItem[], properties: CitationProperties, citation_index: integer}
 
---- at alias CitationProperties { noteIndex: NoteIndex, chapterIndex: ChapterIndex, mode: string? }
+--- at class CitationData
+--- at field citationID CitationId
+--- at field citationItems CitationItem[]
+--- at field properties CitationProperties
+--- at field citation_index integer
 
+--- at class CitationProperties
+--- at field noteIndex NoteIndex,
+--- at field chapterIndex ChapterIndex,
+--- at field mode string?
+--- at field prefix string?
+--- at field suffix string?
+
+
 --- at class NameVariable
 --- at field family string?
 --- at field given string?
@@ -94,15 +105,22 @@
 
 --- at class CiteProc
 --- at field style Style
---- at field sys any
---- at field locales Locale[]
---- at field system_locales Locale[]
---- at field lang string
+--- at field sys CiteProcSys
+--- at field locales table<LanguageCode, Locale>
+--- at field system_locales table<LanguageCode, Locale>
+--- at field lang LanguageCode
 --- at field output_format OutputFormat
 --- at field opt table
 --- at field registry Registry
 --- at field cite_first_note_numbers table<ItemId, NoteIndex>
---- at field locale_tags_info_dict {[LanguageCode]: table}
+--- at field cite_last_note_numbers table<ItemId, NoteIndex>
+--- at field note_citations_map table<NoteIndex, CitationId[]>
+--- at field tainted_item_ids table<ItemId, boolean>
+--- at field disam_irs IrNode[]
+--- at field cite_irs_by_output table<string, IrNode[]>
+--- at field person_names PersonNameIr[]
+--- at field person_names_by_output table<string, PersonNameIr[]>
+--- at field locale_tags_info_dict table<LanguageCode, table>
 local CiteProc = {}
 
 --- at class CiteProcSys
@@ -125,64 +143,61 @@
   if sys.retrieveItem == nil then
     error("\"citeprocSys.retrieveItem\" required")
   end
+  local parsed_style = Style:parse(style)
+  local engine_lang = parsed_style.default_locale
+  if not engine_lang or force_lang then
+    engine_lang = lang or "en-US"
+  end
   --- at type CiteProc
-  local o = {}
+  local o = {
+    style = parsed_style,
+    sys = sys,
+    locales = {},
+    system_locales = {},
+    lang = engine_lang,
+    output_format = LatexWriter:new(),
+    opt = {
+      -- Similar to citeproc-js's development_extensions.wrap_url_and_doi
+      wrap_url_and_doi = false,
+      citation_link = false,
+      title_link = false,
+    },
+    registry = {
+      citations_by_id = {},  -- A map
+      citation_list = {},  -- A list
+      citations_by_item_id = {},  -- A map from item id to a map of citations
+      registry = {},  -- A map of bibliographic meta data
+      reflist = {},  -- list of cited ids
+      uncited_list = {},
+      previous_citation = nil,
+      requires_sorting = false,
+      widest_label = "",
+      maxoffset = 0,
+    },
 
-  o.style = Style:parse(style)
+    cite_first_note_numbers = {},
+    cite_last_note_numbers = {},
+    note_citations_map = {},
 
-  o.sys = sys
-  o.locales = {}
-  o.system_locales = {}
+    tainted_item_ids = {},
 
-  o.lang = o.style.default_locale
-  if not o.lang or force_lang then
-    o.lang = lang or "en-US"
-  end
+    disam_irs = {},
+    -- { <ir1>, <ir2>, ...  }
 
-  o.output_format = LatexWriter:new()
+    cite_irs_by_output = {},
+    -- {
+    --   ["Roe, J"] = {<ir1>},
+    --   ["Doe, J"] = {<ir2>, <ir3>},
+    --   ["Doe, John"] = {<ir2>},
+    --   ["Doe, Jack"] = {<ir2>},
+    -- }
 
-  o.opt = {
-    -- Similar to citeproc-js's development_extensions.wrap_url_and_doi
-    wrap_url_and_doi = false,
-    citation_link = false,
-    title_link = false,
-  }
+    person_names = {},
+    person_names_by_output = {},
 
-  o.registry = {
-    citations_by_id = {},  -- A map
-    citation_list = {},  -- A list
-    citations_by_item_id = {},  -- A map from item id to a map of citations
-    registry = {},  -- A map of bibliographic meta data
-    reflist = {},  -- list of cited ids
-    uncited_list = {},
-    previous_citation = nil,
-    requires_sorting = false,
-    widest_label = "",
-    maxoffset = 0,
+    locale_tags_info_dict = {},
   }
 
-  o.cite_first_note_numbers = {}
-  o.cite_last_note_numbers = {}
-  o.note_citations_map = {}
-
-  o.tainted_item_ids = {}
-
-  o.disam_irs = {}
-  -- { <ir1>, <ir2>, ...  }
-
-  o.cite_irs_by_output = {}
-  -- {
-  --   ["Roe, J"] = {<ir1>},
-  --   ["Doe, J"] = {<ir2>, <ir3>},
-  --   ["Doe, John"] = {<ir2>},
-  --   ["Doe, Jack"] = {<ir2>},
-  -- }
-
-  o.person_names = {}
-  o.person_names_by_output = {}
-
-  o.locale_tags_info_dict = {}
-
   setmetatable(o, { __index = CiteProc })
   return o
 end
@@ -444,15 +459,11 @@
     -- Assert CSL rich-text or HTML-like tagged string
     if cite_item.prefix == "" then
       cite_item.prefix = nil
-    else
-      cite_item.prefix_inlines = InlineElement:parse(cite_item.prefix, the_context, true)
     end
   end
   if cite_item.suffix then
     if cite_item.suffix == "" then
       cite_item.suffix = nil
-    else
-      cite_item.suffix_inlines = InlineElement:parse(cite_item.suffix, the_context, true)
     end
   end
 

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-latex-parser.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-latex-parser.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-latex-parser.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -133,10 +133,11 @@
   local latex_grammar = P{
     "latex_text";
     latex_text = Ct((specials + control_sequence + math + ligatures + specials + V"group" + plain_text)^0),
-    group = P"{" * V"latex_text" * P"}" / function (group_contents)
+    group = C(P"{" * V"latex_text" * P"}") / function (raw, group_contents)
       return {
         type = "group",
         contents = group_contents,
+        raw = raw,
       }
     end,
   }
@@ -348,9 +349,18 @@
   else
     -- Unrecognized command
     if strict then
-      table.insert(inlines, markup.Code:new(token.raw))
+      local raw = token.raw
+      for j = i + 1, #tokens do
+        if type(tokens[j]) == "table" and tokens[j].type == "group" then
+          i = j
+          raw = raw .. latex_parser.convert_token_to_raw(tokens[j])
+        else
+          break
+        end
+      end
+      table.insert(inlines, markup.Code:new(raw))
     else
-      -- Gobble following groupsas pandoc does:
+      -- Gobble following groups as pandoc does:
       -- "Foo \unrecognized{bar}{baz} quz" -> "Foo  quz"
       for j = i + 1, #tokens do
         if type(tokens[j]) == "table" and tokens[j].type == "group" then
@@ -365,6 +375,31 @@
   return inlines, i
 end
 
+--- at param token any
+--- at return string
+function latex_parser.convert_token_to_raw(token)
+  if type(token) == "string" then
+    return token
+  elseif type(token) == "table" then
+    if token.raw then
+      return token.raw
+    elseif token.type == "group" then
+      local raw = "{"
+      for _, token_ in ipairs(token.contents) do
+        raw = raw .. latex_parser.convert_token_to_raw(token_)
+      end
+      raw = raw .. "}"
+      return raw
+    else
+      error(token.type)
+      return ""
+    end
+  else
+    error(type(token))
+    return ""
+  end
+end
+
 -- TODO: raise a warning for unrecognized LaTeX command like `\switchargs`
 function latex_parser.convert_group_to_inlines(token, strict, case_protection, force_add_braces)
   if case_protection then

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-manager.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-manager.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-manager.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -582,6 +582,13 @@
     util.error(string.format("Invalid chapter index '%s'.", chapter_index))
   end
 
+  if citation.properties.prefix then
+    citation.properties.prefix = latex_parser.latex_to_pseudo_html(citation.properties.prefix, true, false)
+  end
+  if citation.properties.suffix then
+    citation.properties.suffix = latex_parser.latex_to_pseudo_html(citation.properties.suffix, true, false)
+  end
+
   -- util.debug(citation)
   return citation
 end
@@ -857,9 +864,12 @@
       self:register_citation_info(tostring(ref_section_index), content)
       if ref_section.engine then
         local citation = self:_make_citation(content)
-        local citation_str = ref_section.engine:process_citation(citation)
-
-        table.insert(output_lines, string.format("\\cslcitation{%s}{%s}", citation.citationID, citation_str))
+        if citation.citationID == "@nocite" then
+          ref_section:_update_uncited_items()
+        else
+          local citation_str = ref_section.engine:process_citation(citation)
+          table.insert(output_lines, string.format("\\cslcitation{%s}{%s}", citation.citationID, citation_str))
+        end
       end
 
     elseif command == "\\csl at aux@bibliography" then

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-node-citation.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-node-citation.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-node-citation.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -184,17 +184,16 @@
 --- at field suffix string?
 --- at field locator string?
 --- at field label string?
---- at field prefix_inlines InlineElement[]?
---- at field suffix_inlines InlineElement[]?
 
 ---comment
 --- at param citation_items CitationItem[]
 --- at param engine CiteProc
---- at param properties table
+--- at param properties CitationProperties
 --- at return string
 function Citation:build_cluster(citation_items, engine, properties)
   properties = properties or {}
   local output_format = engine.output_format
+  --- at type CiteIr[]
   local irs = {}
   citation_items = self:sorted_citation_items(citation_items, engine)
   for _, cite_item in ipairs(citation_items) do
@@ -227,7 +226,7 @@
       -- if layout_affixes then
       --   layout_prefix = layout_affixes.prefix
       -- end
-    local prefix_inlines = citation_items[i].prefix_inlines
+    local prefix_inlines = ir.cite_prefix
     if prefix_inlines then
       -- Prefix is inlines
       local prefix_str = output.SortStringFormat:new():output(prefix_inlines, context)
@@ -262,8 +261,8 @@
 
   local previous_ir
   for i, ir in ipairs(irs) do
-    local cite_prefix = citation_items[i].prefix_inlines
-    local cite_suffix = citation_items[i].suffix_inlines
+    local cite_prefix = ir.cite_prefix
+    local cite_suffix = ir.cite_suffix
     if not ir.collapse_suppressed then
       local cite_inlines = ir:flatten(output_format)
       if #cite_inlines > 0 then
@@ -329,14 +328,28 @@
     has_printed_form = false
   end
 
+  -- Ouput citation affixes
+  if has_printed_form then
+    if properties.prefix and properties.prefix ~= "" then
+      local citation_prefix = util.check_prefix_space_append(properties.prefix)
+      local inlines = InlineElement:parse(citation_prefix, context, true)
+      table.insert(citation_stream, 1, Micro:new(inlines))
+    end
+    if properties.suffix and properties.suffix ~= "" then
+      local citation_suffix = util.check_suffix_prepend(properties.suffix)
+      local inlines = InlineElement:parse(citation_suffix, context, true)
+      table.insert(citation_stream, Micro:new(inlines))
+    end
+  end
+
   local author_only_mode = (properties.mode == "author-only" or
     (#citation_items >= 1 and citation_items[1]["author-only"]))
   if has_printed_form and context.area.layout.affixes and not author_only_mode then
-    if irs[1].cite_prefix then
-      table.insert(citation_stream, 1, PlainText:new(irs[1].cite_prefix))
+    if irs[1].layout_prefix then
+      table.insert(citation_stream, 1, PlainText:new(irs[1].layout_prefix))
     end
-    if irs[#irs].cite_suffix then
-      table.insert(citation_stream, PlainText:new(irs[#irs].cite_suffix))
+    if irs[#irs].layout_suffix then
+      table.insert(citation_stream, PlainText:new(irs[#irs].layout_suffix))
     end
   end
 
@@ -416,8 +429,10 @@
 --- at field disam_level integer
 --- at field disam_str string?
 --- at field cite_delimiter string?
---- at field cite_prefix string?
---- at field cite_suffix string?
+--- at field layout_prefix string?
+--- at field layout_suffix string?
+--- at field cite_prefix InlineElement[]?
+--- at field cite_suffix InlineElement[]?
 
 --- at param cite_item CitationItem
 --- at param output_format OutputFormat
@@ -485,10 +500,19 @@
 
   ir.cite_delimiter = active_layout.delimiter
   if active_layout.affixes then
-    ir.cite_prefix = active_layout.affixes.prefix
-    ir.cite_suffix = active_layout.affixes.suffix
+    ir.layout_prefix = active_layout.affixes.prefix
+    ir.layout_suffix = active_layout.affixes.suffix
   end
 
+  if cite_item.prefix and cite_item.prefix ~= "" then
+    local cite_prefix = util.check_prefix_space_append(cite_item.prefix)
+    ir.cite_prefix = InlineElement:parse(cite_prefix, context, true)
+  end
+  if cite_item.suffix and cite_item.suffix ~= "" then
+    local cite_suffix = util.check_suffix_prepend(cite_item.suffix)
+    ir.cite_suffix = InlineElement:parse(cite_suffix, context, true)
+  end
+
   -- Formattings like font-style are ignored for disambiguation.
   local disam_format = DisamStringFormat:new()
   local inlines = ir:flatten(disam_format)

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-util.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-util.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc-util.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -433,6 +433,46 @@
   return string.sub(str, -#suffix) == suffix
 end
 
+--- at param str string
+--- at return string
+function util.check_prefix_space_append(str)
+  if str == "" then
+    return str
+  end
+  local last_char = uni_utf8.match(str, ".$")
+  if not last_char then
+    return str
+  end
+  if util.is_romanesque(utf8.codepoint(last_char, 1, #last_char)) then
+    return str .. " "
+  elseif string.match(last_char, "[:.;!?]") then
+    return str .. " "
+  elseif string.match(last_char, "[)%],0-9]") then
+    return str .. " "
+  else
+    return str
+  end
+end
+
+--- at param str string
+--- at return string
+function util.check_suffix_prepend(str)
+  if str == "" then
+    return str
+  end
+  local first_char = uni_utf8.match(str, "^.")
+  if not first_char then
+    return str
+  end
+  if util.is_romanesque(utf8.codepoint(first_char, 1, #first_char)) then
+    return " " .. str
+  elseif string.match(first_char, "[)%[]") then
+    return " " .. str
+  else
+    return str
+  end
+end
+
 --- at param str string | number
 --- at return boolean
 function util.is_numeric(str)

Modified: trunk/Master/texmf-dist/scripts/citation-style-language/citeproc.lua
===================================================================
--- trunk/Master/texmf-dist/scripts/citation-style-language/citeproc.lua	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/scripts/citation-style-language/citeproc.lua	2024-09-01 20:46:02 UTC (rev 72157)
@@ -16,7 +16,7 @@
   util = require("citeproc.util")
 end
 
-citeproc.__VERSION__ = "0.6.2"
+citeproc.__VERSION__ = "0.6.3"
 
 citeproc.new = engine.CiteProc.new
 citeproc.util = util

Modified: trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-cite.sty
===================================================================
--- trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-cite.sty	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-cite.sty	2024-09-01 20:46:02 UTC (rev 72157)
@@ -76,17 +76,15 @@
     \tl_if_blank:nTF {#3}
       { \__csl_print_undefined_citation:n {#3} }
       {
-        \seq_clear:N \l__csl_cite_keys_seq
-        \seq_clear:N \l__csl_citation_items_seq
-        \prop_clear:N \l__csl_citation_properties_prop
-        \__csl_process_cite_input:nnn {#1} {#2} {#3}
-        \__csl_process_citation_info:NN \l__csl_cite_keys_seq \l__csl_citation_items_seq
+        \__csl_cite_init:
+        \__csl_collect_citation_items:nnn {#1} {#2} {#3}
+        \__csl_process_citation_info:
         \prop_put:Nnn \l__csl_citation_properties_prop { noteIndex } { 0 }
         \tl_if_empty:nF {#4}
           {
             \prop_put:Nnn \l__csl_citation_properties_prop { mode } {#4}
           }
-        \__csl_make_citation:N \l__csl_citation_info_prop
+        \__csl_make_citation:
       }
   }
 
@@ -101,16 +99,14 @@
         \tl_if_blank:nTF {#3}
           { \__csl_print_undefined_citation:n {#3} }
           {
-            \seq_clear:N \l__csl_cite_keys_seq
-            \seq_clear:N \l__csl_citation_items_seq
-            \prop_clear:N \l__csl_citation_properties_prop
-            \__csl_process_cite_input:nnn {#1} {#2} {#3}
-            \__csl_process_citation_info:NN \l__csl_cite_keys_seq \l__csl_citation_items_seq
+            \__csl_cite_init:
+            \__csl_collect_citation_items:nnn {#1} {#2} {#3}
+            \__csl_process_citation_info:
             \tl_if_empty:nF {#4}
               {
                 \prop_put:Nnn \l__csl_citation_properties_prop { mode } {#4}
               }
-            \__csl_make_citation:N \l__csl_citation_info_prop
+            \__csl_make_citation:
           }
       }
       {
@@ -119,16 +115,14 @@
             \tl_if_blank:nTF {#3}
               { \__csl_print_undefined_citation:n {#3} }
               {
-                \seq_clear:N \l__csl_cite_keys_seq
-                \seq_clear:N \l__csl_citation_items_seq
-                \prop_clear:N \l__csl_citation_properties_prop
-                \__csl_process_cite_input:nnn {#1} {#2} {#3}
-                \__csl_process_citation_info:NN \l__csl_cite_keys_seq \l__csl_citation_items_seq
+                \__csl_cite_init:
+                \__csl_collect_citation_items:nnn {#1} {#2} {#3}
+                \__csl_process_citation_info:
                 \tl_if_empty:nF {#4}
                   {
                     \prop_put:Nnn \l__csl_citation_properties_prop { mode } {#4}
                   }
-                \__csl_make_citation:N \l__csl_citation_info_prop
+                \__csl_make_citation:
               }
           }
       }
@@ -158,11 +152,12 @@
   }
 
 
+\bool_new:N \l__csl_multi_cite_bool
+
 \cs_new:Npn \__csl_cites:
   {
-    \seq_clear:N \l__csl_cite_keys_seq
-    \seq_clear:N \l__csl_citation_items_seq
-    \prop_clear:N \l__csl_citation_properties_prop
+    \__csl_cite_init:
+    \bool_set_true:N \l__csl_multi_cite_bool
     \__csl_next_cites:nnn
   }
 
@@ -174,27 +169,39 @@
           {
             \footnote
               {
-                \__csl_process_citation_info:NN \l__csl_cite_keys_seq \l__csl_citation_items_seq
-                \__csl_make_citation:N \l__csl_citation_info_prop
+                \__csl_process_citation_info:
+                \__csl_make_citation:
               }
           }
           {
-            \__csl_process_citation_info:NN \l__csl_cite_keys_seq \l__csl_citation_items_seq
-            \__csl_make_citation:N \l__csl_citation_info_prop
+            \__csl_process_citation_info:
+            \__csl_make_citation:
           }
       }
       {
-        \__csl_process_cite_input:nnn {#1} {#2} {#3}
+        \__csl_collect_citation_items:nnn {#1} {#2} {#3}
         \__csl_next_cites:nnn
       }
   }
 
 
+\cs_new:Npn \__csl_cite_init:
+  {
+    \bool_set_false:N \l__csl_multi_cite_bool
+    \prop_clear:N \l__csl_citation_info_prop
+    \seq_clear:N \l__csl_cite_keys_seq
+    \seq_clear:N \l__csl_citation_items_seq
+    \prop_clear:N \l__csl_citation_properties_prop
+    \tl_clear:N \l__csl_cite_prefix_tl
+    \tl_clear:N \l__csl_cite_suffix_tl
+  }
+
+
 % Appends the cite key into \l__csl_cite_keys_seq and cite-items into
 % \l__csl_citation_items_seq
 % #1, #2: prenote/postnote
 % #3: keys
-\cs_new:Npn \__csl_process_cite_input:nnn #1#2#3
+\cs_new:Npn \__csl_collect_citation_items:nnn #1#2#3
   {
     \tl_if_novalue:nTF {#2}
       {
@@ -222,12 +229,13 @@
 
 
 \prop_new:N \l__csl_cite_item_prop
-\tl_new:N \l__csl_prefix_tl
-\tl_new:N \l__csl_suffix_tl
 
+% Collect citation items into \l__csl_citation_items_seq
+% Append "{id={ITEM},locator={42},label={page}}" into \l__csl_citation_items_seq
+% #1: prenote
+% #2: postnote
+% #3: key
 \cs_new:Npn \__csl_process_cite_item:nnn #1#2#3
-  % #1: prenote, #2: postnote, #3: key
-  % Save "{id={ITEM},locator={42},label={page}}" into \l__csl_citation_items_seq
   {
     \prop_clear:N \l__csl_cite_item_prop
     \prop_put:Nnn \l__csl_cite_item_prop { id } {#3}
@@ -235,11 +243,12 @@
     %   { \prop_put:Nnn \l__csl_cite_item_prop { suppress-author } { true } }
     % \bool_if:T \l__csl_author_only_bool
     %   { \prop_put:Nnn \l__csl_cite_item_prop { author-only } { true } }
+    \tl_clear:N \l__csl_cite_prefix_tl
+    \tl_clear:N \l__csl_cite_suffix_tl
     \tl_if_empty:nF {#1}
       {
-        \tl_set:Nn \l__csl_prefix_tl {#1}
-        \tl_put_right:NV \l__csl_prefix_tl \l__csl_prefix_separator_tl
-        \prop_put:NnV \l__csl_cite_item_prop { prefix } \l__csl_prefix_tl
+        \tl_set:Nn \l__csl_cite_prefix_tl {#1}
+        \tl_put_right:NV \l__csl_cite_prefix_tl \l__csl_prefix_separator_tl
       }
     \tl_if_empty:nF {#2}
       {
@@ -249,12 +258,26 @@
             \regex_match:nnTF { \d+ } {#2}
               { \__csl_set_locator:nn { page } {#2} }
               {
-                \tl_set:Nn \l__csl_suffix_tl {#2}
-                \tl_put_left:NV \l__csl_suffix_tl \l__csl_suffix_separator_tl
-                \prop_put:NnV \l__csl_cite_item_prop { suffix } \l__csl_suffix_tl
+                \tl_set:Nn \l__csl_cite_suffix_tl {#2}
+                \tl_put_left:NV \l__csl_cite_suffix_tl \l__csl_suffix_separator_tl
               }
           }
       }
+    % The affixes are treated as cite item affixes in a multi-cite command
+    % (like `\cites`). Otherwise they are citation affixes.
+    \bool_if:NTF \l__csl_multi_cite_bool
+      {
+        \tl_if_empty:NF \l__csl_cite_prefix_tl
+          { \prop_put:NnV \l__csl_cite_item_prop { prefix } \l__csl_cite_prefix_tl }
+        \tl_if_empty:NF \l__csl_cite_suffix_tl
+          { \prop_put:NnV \l__csl_cite_item_prop { suffix } \l__csl_cite_suffix_tl }
+      }
+      {
+        \tl_if_empty:NF \l__csl_cite_prefix_tl
+          { \prop_put:NnV \l__csl_citation_properties_prop { prefix } \l__csl_cite_prefix_tl }
+        \tl_if_empty:NF \l__csl_cite_suffix_tl
+          { \prop_put:NnV \l__csl_citation_properties_prop { suffix } \l__csl_cite_suffix_tl }
+      }
     \__csl_serialize_prop:NN \l__csl_cite_item_prop \l_tmpa_tl
     \tl_put_left:NV \l_tmpa_tl { \c_left_brace_str }
     \tl_put_right:NV \l_tmpa_tl { \c_right_brace_str }
@@ -274,10 +297,13 @@
 \msg_new:nnn { citation-style-language } { empty-locator }
   { Empty~ '#1'~ locator. }
 
+\tl_new:N \l__csl_cite_prefix_tl
+\tl_new:N \l__csl_cite_suffix_tl
+
 \keys_define:nn { csl / cite-item }
   {
-    prefix          .prop_put:N = \l__csl_cite_item_prop,
-    suffix          .prop_put:N = \l__csl_cite_item_prop,
+    prefix          .tl_set:N = \l__csl_cite_prefix_tl,
+    suffix          .tl_set:N = \l__csl_cite_suffix_tl,
     locator         .prop_put:N = \l__csl_cite_item_prop,
     label           .prop_put:N = \l__csl_cite_item_prop,
     suppress-author .prop_put:N = \l__csl_cite_item_prop,
@@ -325,13 +351,10 @@
 % Load the cite keys and prepare:
 %   - \l__csl_citation_id_tl
 %   - \l__csl_citation_properties_prop
-%
-% #1: \l__csl_cite_keys_seq
-% #2: \l__csl_citation_items_seq
-\cs_new:Npn \__csl_process_citation_info:NN #1#2
+\cs_new:Npn \__csl_process_citation_info:
   {
-    \__csl_process_citation_id:NN \l__csl_citation_id_tl #1
-    \__csl_get_note_index:N \l__csl_note_index_tl
+    \__csl_process_citation_id:
+    \__csl_get_note_index:
     \prop_put:NnV \l__csl_citation_properties_prop { noteIndex } \l__csl_note_index_tl
     \__csl_make_chapter_property:
     \__csl_add_back_ref_info:
@@ -395,8 +418,7 @@
 \tl_new:N \l__csl_citation_properties_tl
 
 % Write citation info to aux and print the citation contents.
-% #1: \l__csl_citation_info_prop
-\cs_new:Npn \__csl_make_citation:N #1
+\cs_new:Npn \__csl_make_citation:
   {
     \prop_clear:N \l__csl_citation_info_prop
     % citationID
@@ -416,7 +438,7 @@
     % Print the citation string
     \prop_get:NVNTF \g__csl_citations_prop \l__csl_citation_id_tl
       \l__csl_citation_tl
-      { \__csl_print_citation:N \l__csl_citation_tl }
+      { \__csl_print_citation: }
       {
         \bool_if:NTF \l__csl_engine_initialized_bool
           {
@@ -427,7 +449,7 @@
               \char_set_catcode_other:N \%
               \char_set_catcode_other:N \#
               \exp_args:NV \__csl_cite_aux:n \l__csl_citation_info_tl
-              \__csl_print_citation:N \l__csl_citation_tl
+              \__csl_print_citation:
             \group_end:
           }
           {
@@ -471,13 +493,12 @@
 \int_new:N \l__csl_citation_count_int
 \prop_new:N \g__csl_citations_count_prop
 
-\cs_new:Npn \__csl_process_citation_id:NN #1#2
-  % #1: \l__csl_citation_id_tl
-  % #2: \l__csl_cite_keys_seq
-  % Set \l__csl_citation_id_tl = "ITEM-1,ITEM-2 at 4".
+% Load cite keys from `\l__csl_cite_keys_seq` and make `\l__csl_citation_id_tl`.
+% Set \l__csl_citation_id_tl = "ITEM-1,ITEM-2 at 4".
+\cs_new:Npn \__csl_process_citation_id:
   {
     \tl_set:Nx \l__csl_cite_keys_tl
-      { \seq_use:Nn #2 { , } }
+      { \seq_use:Nn \l__csl_cite_keys_seq { , } }
     % \prop_show:N \g__csl_citations_count_prop
     % \tl_show:N \l__csl_cite_keys_tl
     \prop_get:NVNTF \g__csl_citations_count_prop \l__csl_cite_keys_tl
@@ -489,7 +510,7 @@
       { \int_set_eq:NN \l__csl_citation_count_int \c_one_int }
     \prop_gput:NVV \g__csl_citations_count_prop \l__csl_cite_keys_tl
       \l__csl_citation_count_int
-    \tl_set:Nx #1
+    \tl_set:Nx \l__csl_citation_id_tl
       { \l__csl_cite_keys_tl @ \int_use:N \l__csl_citation_count_int }
   }
 
@@ -499,11 +520,11 @@
 
 % Save the note number to \l__csl_note_index_tl
 % TODO: multiple citations in a note
-\cs_new:Npn \__csl_get_note_index:N #1
+\cs_new:Npn \__csl_get_note_index:
   % #1: \l__csl_note_index_tl
   {
     \bool_if:NTF \l__csl_note_bool
-      { \tl_set:Nx #1 { \int_use:c { c@ \@mpfn } } }
+      { \tl_set:Nx \l__csl_note_index_tl { \int_use:c { c@ \@mpfn } } }
       {
         \tl_if_empty:NTF \l__csl_class_tl
           {
@@ -511,9 +532,9 @@
             \int_set_eq:Nc \l_tmpa_int { c@ \@mpfn }
             \int_gincr:N \g__csl_pseudo_note_index_int
             \int_add:Nn \l_tmpa_int { \g__csl_pseudo_note_index_int }
-            \tl_set:Nx #1 { \int_use:N \l_tmpa_int }
+            \tl_set:Nx \l__csl_note_index_tl { \int_use:N \l_tmpa_int }
           }
-          { \tl_set:Nn #1 { 0 } }
+          { \tl_set:Nn \l__csl_note_index_tl { 0 } }
       }
   }
 
@@ -538,11 +559,11 @@
 
 
 % #1: \l__csl_citation_tl
-\cs_new:Npn \__csl_print_citation:N #1
+\cs_new:Npn \__csl_print_citation:
   {
     \bool_if:NT \l__csl_regression_test_bool
-      { \tl_show:N #1 }
-    #1
+      { \tl_show:N \l__csl_citation_tl }
+    \l__csl_citation_tl
   }
 
 
@@ -590,16 +611,19 @@
 
 \cs_new:Npn \__csl_no_cite:n #1
   {
-    \seq_clear:N \l__csl_cite_keys_seq
-    \seq_clear:N \l__csl_citation_items_seq
-    \__csl_process_cite_input:nnn { } { } {#1}
+    \__csl_cite_init:
+    \__csl_collect_citation_items:nnn { } { } {#1}
     \tl_set:Nx \l__csl_cite_items_tl
       { \seq_use:Nn \l__csl_citation_items_seq { , } }
+    \prop_clear:N \l__csl_citation_properties_prop
+    \prop_put:Nnn \l__csl_citation_properties_prop { noteIndex } { 0 }
+    \__csl_make_chapter_property:
+    \__csl_serialize_prop:NN \l__csl_citation_properties_prop \l__csl_citation_properties_tl
     \tl_set:Nx \l__csl_citation_info_tl
       {
         citationID    = { @nocite } ,
-        citationItems = { \l__csl_cite_items_tl } ,
-        properties    = { noteIndex = { 0 } }
+        citationItems = { \tl_use:N \l__csl_cite_items_tl } ,
+        properties    = { \tl_use:N \l__csl_citation_properties_tl }
       }
     \bool_if:NT \l__csl_regression_test_bool
       { \tl_show:N \l__csl_citation_info_tl }

Modified: trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-compatible.sty
===================================================================
--- trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-compatible.sty	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language-compatible.sty	2024-09-01 20:46:02 UTC (rev 72157)
@@ -89,8 +89,8 @@
   {
     \BlockquoteDisable
       {
-        \cs_set_eq:NN \__csl_process_citation_info:NN \use_none:nn
-        \cs_set_eq:NN \__csl_make_citation:N \use_none:n
+        \cs_set_eq:NN \__csl_process_citation_info: \relax
+        \cs_set_eq:NN \__csl_make_citation: \relax
       }
   }
 

Modified: trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language.sty
===================================================================
--- trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language.sty	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/tex/latex/citation-style-language/citation-style-language.sty	2024-09-01 20:46:02 UTC (rev 72157)
@@ -9,7 +9,7 @@
 \RequirePackage{expl3}
 \RequirePackage{xparse}
 
-\ProvidesExplPackage {citation-style-language} {2024-08-21} {0.6.2}
+\ProvidesExplPackage {citation-style-language} {2024-08-28} {0.6.3}
   {Citation Style Language for LaTeX}
 
 \RequirePackage { l3keys2e }

Modified: trunk/Master/texmf-dist/tex/latex/citation-style-language/styles/apa.csl
===================================================================
--- trunk/Master/texmf-dist/tex/latex/citation-style-language/styles/apa.csl	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/texmf-dist/tex/latex/citation-style-language/styles/apa.csl	2024-09-01 20:46:02 UTC (rev 72157)
@@ -14,7 +14,7 @@
     <category citation-format="author-date"/>
     <category field="psychology"/>
     <category field="generic-base"/>
-    <updated>2024-08-06T11:26:59-04:00</updated>
+    <updated>2024-08-24T12:16:51-04:00</updated>
     <rights license="http://creativecommons.org/licenses/by-sa/3.0/">This work is licensed under a Creative Commons Attribution-ShareAlike 3.0 License</rights>
   </info>
   <locale xml:lang="en">
@@ -1619,9 +1619,6 @@
             <if variable="archive DOI URL" match="none">
               <text variable="publisher"/>
             </if>
-            <else>
-              <text variable="archive"/>
-            </else>
           </choose>
         </if>
         <else-if type="post webpage" match="any">
@@ -1660,6 +1657,7 @@
                   <text variable="archive_location" prefix="(" suffix=")"/>
                 </group>
                 <text variable="archive"/>
+                <text variable="archive-place"/>
               </if>
               <else>
                 <group delimiter=" ">
@@ -1666,11 +1664,14 @@
                   <text variable="archive"/>
                   <text variable="archive_location" prefix="(" suffix=")"/>
                 </group>
+                <text variable="archive-place"/>
               </else>
             </choose>
           </if>
+          <else>
+            <text variable="archive"/>
+          </else>
         </choose>
-        <text variable="archive-place"/>
       </group>
     </group>
   </macro>

Modified: trunk/Master/tlpkg/tlpsrc/citation-style-language.tlpsrc
===================================================================
--- trunk/Master/tlpkg/tlpsrc/citation-style-language.tlpsrc	2024-09-01 19:01:55 UTC (rev 72156)
+++ trunk/Master/tlpkg/tlpsrc/citation-style-language.tlpsrc	2024-09-01 20:46:02 UTC (rev 72157)
@@ -1,11 +1,11 @@
 docpattern +f texmf-dist/doc/man/man1/citeproc-lua.*
 binpattern f bin/${ARCH}/citeproc-lua
 
+depend l3kernel
+depend l3packages  # xparse
+depend lua-tinyyaml  # YAML parser
+depend lua-uca
+depend lualibs  # JSON parser
 depend luatex
-depend l3kernel
-depend l3packages
-depend filehook
+depend luaxml
 depend url
-depend luaxml
-depend lua-uca
-depend lualibs



More information about the tex-live-commits mailing list.