How to transfer import statements to the scope of a function argument?

For very good reason, I want to avoid global-level import statements and try to make imports work at the smallest scopes possible, a fantastic use case is the CeTZ canvas, where import draw: * is used in the function body, while cetz itself is imported globally to avoid polluting the name space. I thought it would be helpful from a syntax point of view to alias certain functions (like cetz.canvas) with these import statements “built-in”, this however, does not play well with Typst’s import semantics:

#import "@preview/cetz:0.4.0" as cetz: draw

#let mycanvas(body) = {
	import draw: * // contained to scope
	body
}

#mycanvas({
	circle((0, 0), radius: 1) // simple example
})

Is there some way to “insert” the import in the function definition to the body of a function, that is, to transfer the scope of some import statement?
I wouldn’t be surprised if this was impossible, but it would be interesting to see if a solution to this particular problem was possible, even in a ‘hacky’ way.

Not possible. Best you can do is this:

#import "@preview/cetz:0.4.0" as cetz: draw

#let mycanvas(body) = {
	body(draw)
}

#mycanvas(draw => {
	draw.circle((0, 0), radius: 1) // simple example
    // or
    import draw: *
    circle(...)
})

// or
#mycanvas(((circle,)) => {
	circle((0, 0), radius: 1)
})
1 Like

Thanks for that, unfortunately not quite ideal, but I’ll mark this as solution regardless.