# frozen_string_literal: true module Referator class Footnotes attr_reader :config def initialize(config) self.config = config @references = {} end def make_ref(category:, id:) category = category.to_sym if category.instance_of? String config.categories.exists! category @references[category] ||= [] @references[category].each do |reference| return reference if reference.category == category && reference.id == id end reference = config.repo[category, id] @references[category] << reference render_cite_sup(category:, id:) end def fetch_footnotes = notes def fetch_note(category, id) category = category.to_sym if category.instance_of? String config.categories.exists! category index = 0 config.categories.names.each do |cur_category| (@references[cur_category] ||= []).each do |reference| index += 1 next if cur_category != category return Note.new index, reference if reference.id == id end end raise 'Unused note' end def render_footnotes config.scripts.run( :default, **script_vars( template: :footnotes, notes: notes.to_json, ), ) end def render_cite_sup(category:, id:) category = category.to_sym if category.instance_of? String note = notes.flat_map(&:last).find do |curr_note| curr_note[:category] == String(category).to_sym && curr_note[:id] == String(id) end raise 'Unknown note' if note.nil? config.scripts.run( :default, **script_vars( template: :cite_sup, note: note.to_json, ), ) end private def config=(config) unless config.instance_of? Config raise TypeError, "Expected #{Config}, got #{config.class}" end @config = config end def script_vars(template: 'null', note: 'null', notes: 'null') { template:, notes:, note: }.freeze end def notes index = 0 config.categories.names.to_h do |category| [ category, (@references[category] ||= []) .map { |reference| Note.new (index += 1), reference } .map(&:to_h) .freeze, ] end.freeze end end end