observablehq / runtime

The reactive dataflow runtime that powers Observable Framework and Observable notebooks
https://observablehq.com/@observablehq/how-observable-runs
ISC License
1.01k stars 71 forks source link

module.builtin() is not documented #328

Closed mootari closed 3 weeks ago

mootari commented 2 years ago

Compiled Observable notebooks with file attachments call main.builtin() to register a FileAttachment builtin that is local to the module:

const main = runtime.module();
const fileAttachments = new Map([["chinook.db","https://static.observableusercontent.com/files/b3711cfd9bdf50cbe4e74751164d28e907ce366cd4bf56a39a980a48fdc5f998c42a019716a8033e2b54defdd97e4a55ebe4f6464b4f0678ea0311532605a115"]]);
main.builtin("FileAttachment", runtime.fileAttachments(name => fileAttachments.get(name)));

This is currently the only way to define local builtins, as the second argument of the Module constructor is not exposed via runtime.module(). Unfortunately the method is not documented.

mootari commented 2 years ago

(As an aside, runtime.fileAttachments isn't documented either.)

mbostock commented 1 month ago

Somewhat a mistake that module.builtin was made public. A private setter was added in 2d4da0adeedc88bd61246dbf135550100d62b81e to fix a bug, then made public in e804a8682c98268c83b510bb5698e99d484e4ce6 (without documentation). But we should have preserved the original design where the builtins are specified up-front when the module is constructed. But that would require changing the generated code to look something like this:

const fileAttachments = new Map([["chinook.db","https://static.observableusercontent.com/files/b3711cfd9bdf50cbe4e74751164d28e907ce366cd4bf56a39a980a48fdc5f998c42a019716a8033e2b54defdd97e4a55ebe4f6464b4f0678ea0311532605a115"]]);
const main = runtime.module({FileAttachment: runtime.fileAttachments(name => fileAttachments.get(name))});

And I don’t want to spend the effort to create a new compiler version, so I think we are stuck with this (for now). I guess I’ll document the method but also the caveat that you need to call module.builtin before defining any variables (or else).