Class: Ucode::CodeChart::Writer

Inherits:
Object
  • Object
show all
Defined in:
lib/ucode/code_chart/writer.rb

Overview

Orchestrates extraction + provenance sidecar writing for one block. The Writer is the only thing that touches disk in the CodeChart namespace; everything else is composition.

Output layout (per block):

<output_root>/<block_id>/<U+XXXX>.svg
<output_root>/<block_id>/<U+XXXX>.json   # provenance sidecar

One folder per block keeps each block's output self-contained and discoverable — a downstream consumer (fontisan) can iterate a block's folder without scanning the whole tree.

Idempotent: re-running write on the same inputs produces byte-identical files (SVGs via content check; sidecars via Repo::AtomicWrites#write_atomic's canonical-JSON byte-equality). The Summary tally distinguishes "first run" writes from no-op re-writes.

Defined Under Namespace

Classes: Summary

Instance Method Summary collapse

Constructor Details

#initialize(output_root:, pdf_path:, ucd_version: nil, cache_dir: nil, now: nil, pillar3_source: nil, tier1_sources: nil) ⇒ Writer

Returns a new instance of Writer.

Parameters:

  • output_root (Pathname, String)

    parent directory. The <block_id>/ subdirectory is created inside it.

  • pdf_path (Pathname, String)

    Code Charts PDF (already downloaded by the caller; Writer doesn't fetch).

  • ucd_version (String, nil) (defaults to: nil)

    UCD version to stamp on provenance. nil = resolved via VersionResolver.resolve(nil).

  • cache_dir (Pathname, String, nil) (defaults to: nil)

    font-stream cache directory for the EmbeddedFonts::Source.

  • now (Time, nil) (defaults to: nil)

    timestamp override (for tests).

  • pillar3_source,

    tier1_sources: forwarded to the Extractor.



53
54
55
56
57
58
59
60
61
62
63
# File 'lib/ucode/code_chart/writer.rb', line 53

def initialize(output_root:, pdf_path:, ucd_version: nil,
               cache_dir: nil, now: nil,
               pillar3_source: nil, tier1_sources: nil)
  @output_root = Pathname.new(output_root)
  @pdf_path = Pathname.new(pdf_path)
  @ucd_version = ucd_version || VersionResolver.resolve(nil)
  @cache_dir = cache_dir && Pathname.new(cache_dir)
  @now = now
  @pillar3_source = pillar3_source
  @tier1_sources = tier1_sources
end

Instance Method Details

#write(block) ⇒ Summary

Extracts every codepoint in block and writes <block_id>/<cp>.svg

  • <block_id>/<cp>.json under @output_root. Returns a Summary tally.

Parameters:

Returns:



71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
# File 'lib/ucode/code_chart/writer.rb', line 71

def write(block)
  block_dir = @output_root.join(block.id)
  block_dir.mkpath

  pdf_sha = CodeChart.sha256_of(@pdf_path)

  sidecar = Sidecar.new(output_root: block_dir)
  extractor = Extractor.new(
    block: block,
    pdf_path: @pdf_path,
    cache_dir: @cache_dir,
    pillar3_source: @pillar3_source,
    tier1_sources: @tier1_sources,
  )

  results = extractor.extract
  svgs = 0
  sidecars = 0
  results.each do |result|
    write_svg(block_dir, result)
    svgs += 1
    provenance = CodeChart.build(
      block: block, codepoint: result.codepoint,
      ucd_version: @ucd_version, pdf_path: @pdf_path,
      now: @now,
    )
    sidecar.write(provenance)
    sidecars += 1
  end

  Summary.new(
    block: block.id,
    codepoints_extracted: results.size,
    svgs_written: svgs,
    sidecars_written: sidecars,
    pdf_sha256: pdf_sha,
  )
end