Class: Ucode::Audit::LibraryAuditor

Inherits:
Object
  • Object
show all
Defined in:
lib/ucode/audit/library_auditor.rb

Overview

Orchestrates a library-wide audit pass.

Owns the file-system side: discovers font files under a root path (recursively or not), audits each via FaceAuditor, and assembles a Models::Audit::LibrarySummary combining the per-face reports with cross-face rollups from LibraryAggregator.

Aggregation logic lives in the pure LibraryAggregator; this class stays focused on discovery + per-face auditing + summary assembly. Errors auditing a single file are captured in #skipped so a corrupt file doesn't abort the whole pass.

ucode delta vs fontisan: delegates per-face work to FaceAuditor instead of fontisan's Commands::AuditCommand. The discovery and rollup logic is otherwise identical.

Constant Summary collapse

FONT_EXTENSIONS =
%w[.ttf .otf .ttc .otc .dfont .woff .woff2
.pfb .pfa .svg].freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(root_path, recursive:, options:, reference: nil) ⇒ LibraryAuditor

Returns a new instance of LibraryAuditor.

Parameters:

  • root_path (String, Pathname)

    directory containing fonts

  • recursive (Boolean)

    walk into subdirectories

  • options (Hash)

    forwarded to FaceAuditor (ucd_version, all_codepoints, audit_brief, …). Library-only keys are stripped.

  • reference (CoverageReference, nil) (defaults to: nil)

    baseline forwarded to every per-face FaceAuditor (TODO 25). When nil, each face defaults to UCD-only.



33
34
35
36
37
38
39
40
# File 'lib/ucode/audit/library_auditor.rb', line 33

def initialize(root_path, recursive:, options:, reference: nil)
  @root_path = Pathname.new(root_path)
  @recursive = recursive
  @options = options
  @reference = reference
  @aggregator = LibraryAggregator.new
  @skipped = []
end

Instance Attribute Details

#skippedArray<String> (readonly)

Returns source files that could not be audited, formatted as "path: message".

Returns:

  • (Array<String>)

    source files that could not be audited, formatted as "path: message"



65
66
67
# File 'lib/ucode/audit/library_auditor.rb', line 65

def skipped
  @skipped
end

Instance Method Details

#auditModels::Audit::LibrarySummary



43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
# File 'lib/ucode/audit/library_auditor.rb', line 43

def audit
  paths = discover_font_paths
  reports = paths.flat_map { |p| audit_one(p) }
  rolled_up = aggregates(reports)

  Models::Audit::LibrarySummary.new(
    root_path: @root_path.to_s,
    total_files: paths.size,
    total_faces: reports.size,
    scanned_extensions: scanned_extensions(paths),
    aggregate_metrics: rolled_up[:aggregate_metrics].merge(
      total_size_bytes: paths.sum { |p| File.size(p) },
    ),
    script_coverage: rolled_up[:script_coverage],
    duplicate_groups: rolled_up[:duplicate_groups],
    license_distribution: rolled_up[:license_distribution],
    per_face_reports: reports,
  )
end