Here's a concrete example: If I want to turn this very simple Rust package https://docs.rs/unicode-math-class/latest/unicode_math_class/ into a WebAssembly component using https://github.com/bytecodealliance/cargo-component, what should I call the package, world, and interface?
For instance in the example Rust package, there's these levels of hierarchy:
- package: unicode-math-class on crates.io
- crate: unicode_math_class is the singular lib crate in the package. Rust supports N bin + 1 lib crate per package which maps well-ish to multiple worlds?
- modules: there's no submodules like
serde::de so it's just the root module.
- items: the MathClass enum, REVISION constant, and 'class()' function.
In my brain those map relatively cleanly onto the package/world/interface model like so:
- package:
jcbhmr:unicode-math-class from my username + Rust package name. Sorta Docker-like two-part names.
- world:
unicode_math_class from lib crate name -- unicode-math-class due to no underscores
- interface: since I need to put the
enum math-class {} inside an interface... but the MathClass is in the root module... What should I do? Is there a naming convention like interface crate { ... }? Or mod, root, module, iface, exports, main, lib, it, default, or something else? Single metacharacters like $,_,- aren't allowed 😢. If it had any sub-modules I guess those would map well to serde::de => world serde {}; interface de {}.
WIT snippet of that
package jcbhmr:unicode-math-class;
world unicode-math-class {
// Can't export enum without a wrapping interface! What do you call the interface tho?
export x: interface {
enum math-class { ... }
// No consts; compromise with getter func.
revision: func() -> u8;
// No char type; compromise with string.
class: func(c: string) -> math-class;
}
}
Is there a better way? 🤔
I'm looking for the convention. Or just some general "well here's what I do" ideas. I'm having decision paralysis and I'd like to get some other opinions besides my own biased one.
To add another example to my question: what about other languages? Another ezpz to-WASM language besides Rust is JavaScript https://github.com/bytecodealliance/jco#componentize
Here's my guess as to how something like https://tsdocs.dev/docs/string-width might be paralleled to WASM component WIT:
You've roughly got these hierarchical levels:
- npm package: string-width
- subpath-exports: just
./ (no string-width/emojifier sub-exports)
- the exported items: so just
default fn and Options type in this case.
In my brain I think that could be modeled as:
- package:
jcbhmr:string-width since I'm publishing it + package name
- world: different worlds for each subpath-export. Like
string-width => world string-width {} but string-width/emojify => world string-width-emojify {}. Each world is an "entrypoint" set of imports/exports just like an ES module is.
- interface: you can eliminate the need for a redundant
interface exports { default: func(...) } by just putting the func() on the world. But that doesn't work for modules that export enums, records, or resources. Specifically the options bag record.
WIT snippet of that
package jcbhmr:string-width;
// 'import {...} from "string-width"'
world string-width {
use options.{options};
// ugh. now the function is free of an interface but the record type
// needs one. you might as well just stick them both in the interface?
export default: func(string: string, options: option<options>);
export options;
}
interface options {
record options {
ambiguous-is-narrow: bool,
count-ansi-escape-codes: bool,
}
}
Is there a better way? 🤔
no, the string-width/emojify export doesn't actually exist
As you might be able to tell, I'm a bit puzzled about when/how to use interfaces and how to name them idiomatically when they get in the way of flatter hierarchies. I'm trying to understand the concepts that package/world/interface are supposed to represent and apply them to existing programming concepts that
I know. Thanks for reading my TED talk lol
p.s. has this already been discussed somewhere/somehow? it must've...
Here's a concrete example: If I want to turn this very simple Rust package https://docs.rs/unicode-math-class/latest/unicode_math_class/ into a WebAssembly component using https://github.com/bytecodealliance/cargo-component, what should I call the package, world, and interface?
For instance in the example Rust package, there's these levels of hierarchy:
serde::deso it's just the root module.In my brain those map relatively cleanly onto the package/world/interface model like so:
jcbhmr:unicode-math-classfrom my username + Rust package name. Sorta Docker-like two-part names.from lib crate name --unicode_math_classunicode-math-classdue to no underscoresenum math-class {}inside an interface... but theMathClassis in the root module... What should I do? Is there a naming convention likeinterface crate { ... }? Ormod,root,module,iface,exports,main,lib,it,default, or something else? Single metacharacters like$,_,-aren't allowed 😢. If it had any sub-modules I guess those would map well toserde::de=>world serde {}; interface de {}.WIT snippet of that
Is there a better way? 🤔
I'm looking for the convention. Or just some general "well here's what I do" ideas. I'm having decision paralysis and I'd like to get some other opinions besides my own biased one.
To add another example to my question: what about other languages? Another ezpz to-WASM language besides Rust is JavaScript https://github.com/bytecodealliance/jco#componentize
Here's my guess as to how something like https://tsdocs.dev/docs/string-width might be paralleled to WASM component WIT:
You've roughly got these hierarchical levels:
./(nostring-width/emojifiersub-exports)defaultfn andOptionstype in this case.In my brain I think that could be modeled as:
jcbhmr:string-widthsince I'm publishing it + package namestring-width=>world string-width {}butstring-width/emojify=>world string-width-emojify {}. Each world is an "entrypoint" set of imports/exports just like an ES module is.interface exports { default: func(...) }by just putting thefunc()on the world. But that doesn't work for modules that export enums, records, or resources. Specifically theoptionsbag record.WIT snippet of that
Is there a better way? 🤔
no, the
string-width/emojifyexport doesn't actually existAs you might be able to tell, I'm a bit puzzled about when/how to use interfaces and how to name them idiomatically when they get in the way of flatter hierarchies. I'm trying to understand the concepts that package/world/interface are supposed to represent and apply them to existing programming concepts that
I know. Thanks for reading my TED talk lol
p.s. has this already been discussed somewhere/somehow? it must've...