@@ -32,28 +32,25 @@ import (
3232 " github.com/extism/go-pdk"
3333)
3434
35- // export greet
35+ // go:wasmexport greet
3636func greet () int32 {
3737 input := pdk.Input ()
3838 greeting := ` Hello, ` + string (input) + ` !`
3939 pdk.OutputString (greeting)
4040 return 0
4141}
42-
43- func main () {}
4442```
4543
4644Some things to note about this code:
4745
48- 1 . The ` //export greet ` comment is required. This marks the greet function as an
46+ 1 . The ` //go:wasmexport greet ` comment is required. This marks the greet function as an
4947 export with the name ` greet ` that can be called by the host.
50- 2 . We need a ` main ` but it is unused.
51- 3 . Exports in the Go PDK are coded to the raw ABI. You get parameters from the
48+ 2 . Exports in the Go PDK are coded to the raw ABI. You get parameters from the
5249 host by calling
5350 [ pdk.Input* functions] ( https://pkg.go.dev/github.com/extism/go-pdk#Input ) and
5451 you send returns back with the
5552 [ pdk.Output* functions] ( https://pkg.go.dev/github.com/extism/go-pdk#Output ) .
56- 4 . An Extism export expects an i32 return code. ` 0 ` is success and ` 1 ` is a
53+ 3 . An Extism export expects an i32 return code. ` 0 ` is success and ` 1 ` is a
5754 failure.
5855
5956Install the ` tinygo ` compiler:
@@ -68,7 +65,7 @@ platform.
6865Compile this with the command:
6966
7067``` bash
71- tinygo build -o plugin.wasm -target wasi main.go
68+ tinygo build -o plugin.wasm -target wasip1 -buildmode=c-shared main.go
7269```
7370
7471We can now test ` plugin.wasm ` using the
@@ -79,7 +76,7 @@ extism call plugin.wasm greet --input "Benjamin" --wasi
7976# => Hello, Benjamin!
8077```
8178
82- > ** Note** : Currently ` wasi ` must be provided for all Go plug-ins even if they
79+ > ** Note** : Currently ` wasip1 ` must be provided for all Go plug-ins even if they
8380> don't need system access, however this will eventually be optional.
8481
8582> ** Note** : We also have a web-based, plug-in tester called the
@@ -92,7 +89,7 @@ use [pdk.SetError](https://pkg.go.dev/github.com/extism/go-pdk#SetError) or
9289[ pdk.SetErrorString] ( https://pkg.go.dev/github.com/extism/go-pdk#SetErrorString ) :
9390
9491``` go
95- // export greet
92+ // go:wasmexport greet
9693func greet () int32 {
9794 name := string (pdk.Input ())
9895 if name == " Benjamin" {
@@ -110,6 +107,7 @@ Now when we try again:
110107``` bash
111108extism call plugin.wasm greet --input=" Benjamin" --wasi
112109# => Error: Sorry, we don't greet Benjamins!
110+ # => returned non-zero exit code: 1
113111echo $? # print last status code
114112# => 1
115113extism call plugin.wasm greet --input=" Zach" --wasi
@@ -134,7 +132,7 @@ type Sum struct {
134132 Sum int ` json:"sum"`
135133}
136134
137- // export add
135+ // go:wasmexport add
138136func add () int32 {
139137 params := Add{}
140138 // use json input helper, which automatically unmarshals the plugin input into your struct
@@ -145,7 +143,7 @@ func add() int32 {
145143 }
146144 sum := Sum{Sum: params.A + params.B }
147145 // use json output helper, which automatically marshals your struct to the plugin output
148- output , err := pdk.OutputJSON (sum)
146+ _ , err := pdk.OutputJSON (sum)
149147 if err != nil {
150148 pdk.SetError (err)
151149 return 1
@@ -167,7 +165,7 @@ that exists across every function call. Here is a trivial example using
167165[ pdk.GetConfig] ( https://pkg.go.dev/github.com/extism/go-pdk#GetConfig ) :
168166
169167``` go
170- // export greet
168+ // go:wasmexport greet
171169func greet () int32 {
172170 user , ok := pdk.GetConfig (" user" )
173171 if !ok {
@@ -195,7 +193,7 @@ will persist across function calls. These variables will persist as long as the
195193host has loaded and not freed the plug-in.
196194
197195``` go
198- // export count
196+ // go:wasmexport count
199197func count () int32 {
200198 count := pdk.GetVarInt (" count" )
201199 count = count + 1
@@ -220,7 +218,7 @@ you to use the host application to log without having to give the plug-in
220218permission to make syscalls.
221219
222220``` go
223- // export log_stuff
221+ // go:wasmexport log_stuff
224222func logStuff () int32 {
225223 pdk.Log (pdk.LogInfo , " An info log!" )
226224 pdk.Log (pdk.LogDebug , " A debug log!" )
@@ -252,7 +250,7 @@ Sometimes it is useful to let a plug-in
252250[ See this example] ( example/http/tiny_main.go )
253251
254252``` go
255- // export http_get
253+ // go:wasmexport http_get
256254func httpGet () int32 {
257255 // create an HTTP Request (withuot relying on WASI), set headers as needed
258256 req := pdk.NewHTTPRequest (pdk.MethodGet , " https://jsonplaceholder.typicode.com/todos/1" )
@@ -304,7 +302,7 @@ We should be able to call this function as a normal Go function. Note that we
304302need to manually handle the pointer casting:
305303
306304```go
307- // export hello_from_python
305+ // go:wasmexport hello_from_python
308306func helloFromPython() int32 {
309307 msg := " An argument to send to Python"
310308 mem := pdk.AllocateString (msg)
@@ -356,11 +354,29 @@ python3 app.py
356354
357355## Reactor modules
358356
359- Since TinyGo doesn't support
360- [ Reactor modules] ( https://dylibso.com/blog/wasi-command-reactor/ ) yet, If you
361- want to use WASI inside your Reactor module functions (exported functions other
362- than ` main ` ), you'll need to import ` wasi-reactor ` module which makes sure libc
363- and go runtime are properly initialized:
357+ Since TinyGo version 0.34.0, the compiler has native support for
358+ [ Reactor modules] ( https://dylibso.com/blog/wasi-command-reactor/ ) .
359+
360+ Make sure you invoke the compiler with the ` -buildmode=c-shared ` flag
361+ so that libc and the Go runtime are properly initialized:
362+
363+ ``` bash
364+ cd example/reactor
365+ tinygo build -target wasip1 -buildmode=c-shared -o reactor.wasm ./tiny_main.go
366+ extism call ./reactor.wasm read_file --input " ./test.txt" --allow-path . --wasi --log-level info
367+ # => Hello World!
368+ ```
369+
370+ ### Note on TinyGo 0.33.0 and earlier
371+
372+ TinyGo versions below 0.34.0 do not support
373+ [ Reactor modules] ( https://dylibso.com/blog/wasi-command-reactor/ ) .
374+ If you want to use WASI inside your Reactor module functions (exported functions other
375+ than ` main ` ). You can however import the ` wasi-reactor ` module to ensure that libc
376+ and go runtime are initialized as expected:
377+
378+ Moreover, older versions may not provide the special ` //go:wasmexport `
379+ directive, and instead use ` //export ` .
364380
365381``` go
366382package main
@@ -389,7 +405,7 @@ func main() {}
389405```
390406
391407``` bash
392- tinygo build -target wasi -o reactor.wasm .\ t iny_main.go
408+ tinygo build -target wasip1 -o reactor.wasm ./ tiny_main.go
393409extism call ./reactor.wasm read_file --input " ./test.txt" --allow-path . --wasi --log-level info
394410# => Hello World!
395411```
0 commit comments