Skip to content

Parametric packaging? (e.g., replicating @iconify-json/<icon-set> from Iconify's NPM packages) #1101

Description

@jmuchovej

Description

Not quite an issue, more-so a feature request. I'm in the middle of porting https://github.com/iconify/icon-sets to Typst so we can have our pick of SVG icons (without needing them as fonts 🎉)!

Iconify has a really slick layout (mostly for tree-shaking, if I understand correctly) where users can install an icon-set's JSON to support it (rather than having to install all 150+ icon sets, which turns in to something like 200K+ icons).

I'm not sure that Typst has/needs tree-shaking the way that web-oriented projects do, but the full package I've built (https://github.com/jmuchovej/typst-iconify) is north of 1GB because it has almost all the icons included.

There's two packaging strategies I can think of for the typst-iconify project:

  1. typst-iconify just packages up the entire Iconify library (200K+ icons, relevant JSON/SVGs is ~950MB as of 15 Oct 2024).
  2. typst-iconify has some kind setup like... @preview/iconify (core library) and users can add @preview/iconify-{iconset} where {iconset} might be academicons, carbon, catppuccin, fa (font awesome), etc.

(1) is by far the most straightforward, but it introduces some critical problems:

  1. Installation requires downloading ~950MB (or more, in the future) worth of SVGS, most of which will go unused.
  2. Once typst-iconify is stable, I suspect that the icon sets will update far more frequently than the core package code – having some way to separate these concerns would be ideal – however I'm not sure how. (It appears that @iconify-json/{iconset} essentially installs the corresponding JSON file in a shared directory that other @iconify/... tools know how to access. (If Typst supports similarly, I'd be more than happy to explore that, I just don't know where/if that's possible.)

In the current packaging approach, where everything is namedspaced under @preview/... I don't think this avoids the patch-version explosion (though it could still cause significant version explosion because the icon sets appear to be upgraded pretty regularly).

So, this leads me to my questions:

  1. Is there a way to support something like the following – where line 2 essentially adds the academicons JSON files that @preview/iconify knows how to parse to some shared location?
    1 | #import "@preview/iconify:0.1.0": icon
    2 | #import "@preview/iconify-academicons:1.2.8"
    3 | 
    4 | #icon("academicon:arxiv")
  2. If ☝️ is possible, how would I achieve this? Particularly, this introduces a second set of problems:
    1. Can Typst, functionally, write temporary files (or similar)? (i.e., If @preview/iconify dynamically loads SVG data, the packaged code in @preview/iconify-academicons will be an SVG string, but image requires a file-path.
    2. Is it possible to essentially write to a cache in this manner, or would it be "more typst-ian" to recompute all this data upon initial compilation? (i.e., if someone closes a doc, then reopens it later.)
  3. How concerned are Typst with "patch bloat" from packages? (e.g., the split-package route I've described/favored would introduce over 150 packages, each with their own versioning/etc. I'd have them configured to auto-update, but I don't want these to end up back-logging other package updates, since they're definitely low priority. 😅)

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions