@ruby/head-wasm-wasi 2.3.0 → 2.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,336 +1,7 @@
1
1
  # @ruby/head-wasm-wasi
2
2
 
3
- WebAssembly port of CRuby with WASI.
3
+ [![npm version](https://badge.fury.io/js/@ruby%2Fhead-wasm-wasi.svg)](https://www.npmjs.com/package/@ruby/head-wasm-wasi)
4
4
 
5
- This package distributes the latest `master` branch of CRuby.
5
+ This package provides WebAssembly binaries of CRuby built from the latest `HEAD` source code targeting WASI-compatible environments.
6
6
 
7
- ## Installation
8
-
9
- For installing `@ruby/head-wasm-wasi` family, just run this command in your shell:
10
-
11
- ```console
12
- $ npm install --save @ruby/head-wasm-wasi@latest
13
- # or if you want the nightly snapshot
14
- $ npm install --save @ruby/head-wasm-wasi@next
15
- # or you can specify the exact snapshot version
16
- $ npm install --save @ruby/head-wasm-wasi@2.3.0-2023-11-26-a
17
- ```
18
-
19
- ## Quick Start (for Node.js)
20
-
21
- See [the example project](https://github.com/ruby/ruby.wasm/tree/main/packages/npm-packages/ruby-wasm-wasi/example) for more details.
22
-
23
- ```javascript
24
- import fs from "fs/promises";
25
- import { DefaultRubyVM } from "@ruby/wasm-wasi/dist/node.cjs.js";
26
-
27
- const main = async () => {
28
- const binary = await fs.readFile(
29
- // Tips: Replace the binary with debug info if you want symbolicated stack trace.
30
- // (only nightly release for now)
31
- // "./node_modules/@ruby/head-wasm-wasi/dist/ruby.debug+stdlib.wasm"
32
- "./node_modules/@ruby/head-wasm-wasi/dist/ruby.wasm"
33
- );
34
- const module = await WebAssembly.compile(binary);
35
- const { vm } = await DefaultRubyVM(module);
36
-
37
- vm.eval(`
38
- luckiness = ["Lucky", "Unlucky"].sample
39
- puts "You are #{luckiness}"
40
- `);
41
- };
42
-
43
- main();
44
- ```
45
-
46
- Then you can run the example project in your terminal:
47
-
48
- ```console
49
- $ node --experimental-wasi-unstable-preview1 index.node.js
50
- ```
51
-
52
- ## Quick Start (for Browser)
53
-
54
- In browser, you need a WASI polyfill. See [the example project](https://github.com/ruby/ruby.wasm/tree/main/packages/npm-packages/ruby-wasm-wasi/example) for more details.
55
-
56
- ```html
57
- <html>
58
- <script src="https://cdn.jsdelivr.net/npm/@ruby/wasm-wasi@latest/dist/browser.umd.js"></script>
59
- <script>
60
- const { DefaultRubyVM } = window["ruby-wasm-wasi"];
61
- const main = async () => {
62
- // Fetch and instantiate WebAssembly binary
63
- const response = await fetch(
64
- // Tips: Replace the binary with debug info if you want symbolicated stack trace.
65
- // (only nightly release for now)
66
- // "https://cdn.jsdelivr.net/npm/@ruby/head-wasm-wasi@next/dist/ruby.debug+stdlib.wasm"
67
- "https://cdn.jsdelivr.net/npm/@ruby/head-wasm-wasi@latest/dist/ruby.wasm"
68
- );
69
- const buffer = await response.arrayBuffer();
70
- const module = await WebAssembly.compile(buffer);
71
- const { vm } = await DefaultRubyVM(module);
72
-
73
- vm.printVersion();
74
- vm.eval(`
75
- require "js"
76
- luckiness = ["Lucky", "Unlucky"].sample
77
- JS::eval("document.body.innerText = '#{luckiness}'")
78
- `);
79
- };
80
-
81
- main();
82
- </script>
83
- <body></body>
84
- </html>
85
- ```
86
-
87
- ## GC limitation with JavaScript interoperability
88
-
89
- Since JavaScript's GC system and Ruby's GC system are separated and not cooperative, they cannot collect cyclic references between JavaScript and Ruby objects.
90
-
91
- The following code will cause a memory leak:
92
-
93
- ```javascript
94
- class JNode {
95
- setRNode(rnode) {
96
- this.rnode = rnode;
97
- }
98
- }
99
- jnode = new JNode();
100
-
101
- rnode = vm.eval(`
102
- class RNode
103
- def set_jnode(jnode)
104
- @jnode = jnode
105
- end
106
- end
107
- RNode.new
108
- `);
109
-
110
- rnode.call("set_jnode", vm.wrap(jnode));
111
- jnode.setRNode(rnode);
112
- ```
113
-
114
- <!-- The APIs section was generated by `npx documentation readme ../ruby-wasm-wasi/dist/index.esm.js --section=APIs` -->
115
-
116
- ## APIs
117
-
118
- <!-- Generated by documentation.js. Update this documentation by updating the source code. -->
119
-
120
- #### Table of Contents
121
-
122
- - [RubyVM](#rubyvm)
123
- - [Examples](#examples)
124
- - [initialize](#initialize)
125
- - [Parameters](#parameters)
126
- - [setInstance](#setinstance)
127
- - [Parameters](#parameters-1)
128
- - [addToImports](#addtoimports)
129
- - [Parameters](#parameters-2)
130
- - [printVersion](#printversion)
131
- - [eval](#eval)
132
- - [Parameters](#parameters-3)
133
- - [Examples](#examples-1)
134
- - [evalAsync](#evalasync)
135
- - [Parameters](#parameters-4)
136
- - [Examples](#examples-2)
137
- - [wrap](#wrap)
138
- - [Parameters](#parameters-5)
139
- - [Examples](#examples-3)
140
- - [RbValue](#rbvalue)
141
- - [call](#call)
142
- - [Parameters](#parameters-6)
143
- - [Examples](#examples-4)
144
- - [toPrimitive](#toprimitive)
145
- - [Parameters](#parameters-7)
146
- - [toString](#tostring)
147
- - [toJS](#tojs)
148
- - [RbError](#rberror)
149
-
150
- ### RubyVM
151
-
152
- A Ruby VM instance
153
-
154
- #### Examples
155
-
156
- ```javascript
157
- const wasi = new WASI();
158
- const vm = new RubyVM();
159
- const imports = {
160
- wasi_snapshot_preview1: wasi.wasiImport,
161
- };
162
-
163
- vm.addToImports(imports);
164
-
165
- const instance = await WebAssembly.instantiate(rubyModule, imports);
166
- await vm.setInstance(instance);
167
- wasi.initialize(instance);
168
- vm.initialize();
169
- ```
170
-
171
- #### initialize
172
-
173
- Initialize the Ruby VM with the given command line arguments
174
-
175
- ##### Parameters
176
-
177
- - `args` The command line arguments to pass to Ruby. Must be
178
- an array of strings starting with the Ruby program name. (optional, default `["ruby.wasm","--disable-gems","-e_=0"]`)
179
-
180
- #### setInstance
181
-
182
- Set a given instance to interact JavaScript and Ruby's
183
- WebAssembly instance. This method must be called before calling
184
- Ruby API.
185
-
186
- ##### Parameters
187
-
188
- - `instance` The WebAssembly instance to interact with. Must
189
- be instantiated from a Ruby built with JS extension, and built
190
- with Reactor ABI instead of command line.
191
-
192
- #### addToImports
193
-
194
- Add intrinsic import entries, which is necessary to interact JavaScript
195
- and Ruby's WebAssembly instance.
196
-
197
- ##### Parameters
198
-
199
- - `imports` The import object to add to the WebAssembly instance
200
-
201
- #### printVersion
202
-
203
- Print the Ruby version to stdout
204
-
205
- #### eval
206
-
207
- Runs a string of Ruby code from JavaScript
208
-
209
- ##### Parameters
210
-
211
- - `code` The Ruby code to run
212
-
213
- ##### Examples
214
-
215
- ```javascript
216
- vm.eval("puts 'hello world'");
217
- const result = vm.eval("1 + 2");
218
- console.log(result.toString()); // 3
219
- ```
220
-
221
- Returns **any** the result of the last expression
222
-
223
- #### evalAsync
224
-
225
- Runs a string of Ruby code with top-level `JS::Object#await`
226
- Returns a promise that resolves when execution completes.
227
-
228
- ##### Parameters
229
-
230
- - `code` The Ruby code to run
231
-
232
- ##### Examples
233
-
234
- ```javascript
235
- const text = await vm.evalAsync(`
236
- require 'js'
237
- response = JS.global.fetch('https://example.com').await
238
- response.text.await
239
- `);
240
- console.log(text.toString()); // <html>...</html>
241
- ```
242
-
243
- Returns **any** a promise that resolves to the result of the last expression
244
-
245
- #### wrap
246
-
247
- Wrap a JavaScript value into a Ruby JS::Object
248
-
249
- ##### Parameters
250
-
251
- - `value` The value to convert to RbValue
252
-
253
- ##### Examples
254
-
255
- ```javascript
256
- const hash = vm.eval(`Hash.new`);
257
- hash.call("store", vm.eval(`"key1"`), vm.wrap(new Object()));
258
- ```
259
-
260
- Returns **any** the RbValue object representing the given JS value
261
-
262
- ### RbValue
263
-
264
- A RbValue is an object that represents a value in Ruby
265
-
266
- #### call
267
-
268
- Call a given method with given arguments
269
-
270
- ##### Parameters
271
-
272
- - `callee` name of the Ruby method to call
273
- - `args` **...any** arguments to pass to the method. Must be an array of RbValue
274
-
275
- ##### Examples
276
-
277
- ```javascript
278
- const ary = vm.eval("[1, 2, 3]");
279
- ary.call("push", 4);
280
- console.log(ary.call("sample").toString());
281
- ```
282
-
283
- #### toPrimitive
284
-
285
- - **See**: <https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/Symbol/toPrimitive>
286
-
287
- ##### Parameters
288
-
289
- - `hint` Preferred type of the result primitive value. `"number"`, `"string"`, or `"default"`.
290
-
291
- #### toString
292
-
293
- Returns a string representation of the value by calling `to_s`
294
-
295
- #### toJS
296
-
297
- Returns a JavaScript object representation of the value
298
- by calling `to_js`.
299
-
300
- Returns null if the value is not convertible to a JavaScript object.
301
-
302
- ### RbError
303
-
304
- **Extends Error**
305
-
306
- Error class thrown by Ruby execution
307
-
308
- ## Building the package from source
309
-
310
- The instructions for building a Ruby targeting WebAssembly are available [here](https://github.com/ruby/ruby.wasm#building-from-source).
311
-
312
- Then, you can run the following command in your shell:
313
-
314
- ```console
315
- # Check the directory structure of your Ruby build
316
- $ tree -L 3 path/to/wasm32-unknown-wasi-full-js/
317
- path/to/wasm32-unknown-wasi-full-js/
318
- ├── usr
319
- │ └── local
320
- │ ├── bin
321
- │ ├── include
322
- │ ├── lib
323
- │ └── share
324
- └── var
325
- └── lib
326
- └── gems
327
- $ ./build-package.sh path/to/wasm32-unknown-wasi-full-js/
328
- Generating "/Users/katei/.ghq/github.com/ruby/ruby.wasm/packages/ruby-head-wasm-wasi/src/bindgen/intrinsics.js"
329
- Generating "/Users/katei/.ghq/github.com/ruby/ruby.wasm/packages/ruby-head-wasm-wasi/src/bindgen/rb-abi-guest.d.ts"
330
- Generating "/Users/katei/.ghq/github.com/ruby/ruby.wasm/packages/ruby-head-wasm-wasi/src/bindgen/rb-abi-guest.js"
331
- Generating "/Users/katei/.ghq/github.com/ruby/ruby.wasm/packages/ruby-head-wasm-wasi/src/bindgen/rb-js-abi-host.d.ts"
332
- Generating "/Users/katei/.ghq/github.com/ruby/ruby.wasm/packages/ruby-head-wasm-wasi/src/bindgen/rb-js-abi-host.js"
333
-
334
- src/index.ts → dist/index.umd.js, dist/index.esm.js, dist/index.cjs.js...
335
- created dist/index.umd.js, dist/index.esm.js, dist/index.cjs.js in 682ms
336
- ```
7
+ See [`@ruby/wasm-wasi`](https://github.com/ruby/ruby.wasm/blob/main/packages/npm-packages/ruby-wasm-wasi/README.md) for how to use this package.