goscript 0.1.0 → 0.1.2
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 +267 -255
- package/cmd/goscript/cmd-test.go +286 -0
- package/cmd/goscript/cmd-test_test.go +76 -0
- package/cmd/goscript/cmd_compile.go +9 -0
- package/cmd/goscript/main.go +1 -0
- package/compiler/build-flags.go +38 -0
- package/compiler/compile-request.go +33 -0
- package/compiler/compiler.go +1 -1
- package/compiler/compliance_test.go +0 -10
- package/compiler/config.go +2 -0
- package/compiler/gotest/owner.go +24 -0
- package/compiler/gotest/package-result.go +69 -0
- package/compiler/gotest/request.go +210 -0
- package/compiler/gotest/result.go +28 -0
- package/compiler/gotest/runner.go +1225 -0
- package/compiler/gotest/runner_test.go +1271 -0
- package/compiler/gotest/test.go +9 -0
- package/compiler/index.test.ts +1 -1
- package/compiler/lowered-program.go +80 -21
- package/compiler/lowering.go +6754 -602
- package/compiler/override-facts.go +357 -0
- package/compiler/override-registry.go +52 -190
- package/compiler/override-registry_test.go +182 -0
- package/compiler/package-graph.go +50 -27
- package/compiler/package-graph_test.go +99 -9
- package/compiler/package-test-function.go +9 -0
- package/compiler/package-test-graph-package.go +40 -0
- package/compiler/package-test-graph-variant.go +129 -0
- package/compiler/package-test-graph.go +112 -0
- package/compiler/package-test-graph_test.go +202 -0
- package/compiler/runtime-contract.go +229 -29
- package/compiler/runtime-contract_test.go +44 -30
- package/compiler/semantic-model-types.go +25 -6
- package/compiler/semantic-model.go +819 -74
- package/compiler/semantic-model_test.go +104 -0
- package/compiler/service.go +10 -4
- package/compiler/skeleton_test.go +2777 -524
- package/compiler/tsworkspace/owner-process-unix_test.go +72 -0
- package/compiler/tsworkspace/owner.go +342 -0
- package/compiler/tsworkspace/owner_test.go +93 -0
- package/compiler/tsworkspace/result.go +17 -0
- package/compiler/tsworkspace/tool-process-other.go +14 -0
- package/compiler/tsworkspace/tool-process-unix.go +19 -0
- package/compiler/typescript-emitter.go +576 -86
- package/compiler/wasm/compile.go +1 -1
- package/compiler/wasm/compile_test.go +61 -11
- package/compiler/wasm_api.go +172 -7
- package/dist/gs/builtin/builtin.d.ts +40 -3
- package/dist/gs/builtin/builtin.js +430 -22
- package/dist/gs/builtin/builtin.js.map +1 -1
- package/dist/gs/builtin/channel.d.ts +32 -10
- package/dist/gs/builtin/channel.js +119 -25
- package/dist/gs/builtin/channel.js.map +1 -1
- package/dist/gs/builtin/defer.d.ts +1 -0
- package/dist/gs/builtin/defer.js +12 -2
- package/dist/gs/builtin/defer.js.map +1 -1
- package/dist/gs/builtin/hostio.d.ts +9 -0
- package/dist/gs/builtin/hostio.js +25 -0
- package/dist/gs/builtin/hostio.js.map +1 -1
- package/dist/gs/builtin/map.js +40 -6
- package/dist/gs/builtin/map.js.map +1 -1
- package/dist/gs/builtin/print.js.map +1 -1
- package/dist/gs/builtin/slice.d.ts +64 -10
- package/dist/gs/builtin/slice.js +619 -244
- package/dist/gs/builtin/slice.js.map +1 -1
- package/dist/gs/builtin/type.d.ts +7 -2
- package/dist/gs/builtin/type.js +128 -29
- package/dist/gs/builtin/type.js.map +1 -1
- package/dist/gs/builtin/varRef.d.ts +7 -0
- package/dist/gs/builtin/varRef.js +23 -0
- package/dist/gs/builtin/varRef.js.map +1 -1
- package/dist/gs/bytes/buffer.gs.js +74 -70
- package/dist/gs/bytes/buffer.gs.js.map +1 -1
- package/dist/gs/bytes/iter.gs.js +13 -13
- package/dist/gs/bytes/iter.gs.js.map +1 -1
- package/dist/gs/bytes/reader.gs.js +20 -18
- package/dist/gs/bytes/reader.gs.js.map +1 -1
- package/dist/gs/compress/zlib/index.d.ts +26 -0
- package/dist/gs/compress/zlib/index.js +168 -0
- package/dist/gs/compress/zlib/index.js.map +1 -0
- package/dist/gs/context/context.d.ts +6 -5
- package/dist/gs/context/context.js +17 -12
- package/dist/gs/context/context.js.map +1 -1
- package/dist/gs/crypto/ecdh/index.d.ts +52 -0
- package/dist/gs/crypto/ecdh/index.js +226 -0
- package/dist/gs/crypto/ecdh/index.js.map +1 -0
- package/dist/gs/crypto/ed25519/index.d.ts +34 -0
- package/dist/gs/crypto/ed25519/index.js +160 -0
- package/dist/gs/crypto/ed25519/index.js.map +1 -0
- package/dist/gs/crypto/internal/constanttime/index.d.ts +4 -0
- package/dist/gs/crypto/internal/constanttime/index.js +18 -0
- package/dist/gs/crypto/internal/constanttime/index.js.map +1 -0
- package/dist/gs/crypto/internal/fips140deps/byteorder/index.d.ts +1 -0
- package/dist/gs/crypto/internal/fips140deps/byteorder/index.js +2 -0
- package/dist/gs/crypto/internal/fips140deps/byteorder/index.js.map +1 -0
- package/dist/gs/crypto/internal/fips140deps/godebug/index.d.ts +1 -0
- package/dist/gs/crypto/internal/fips140deps/godebug/index.js +2 -0
- package/dist/gs/crypto/internal/fips140deps/godebug/index.js.map +1 -0
- package/dist/gs/crypto/rand/index.d.ts +2 -0
- package/dist/gs/crypto/rand/index.js +85 -0
- package/dist/gs/crypto/rand/index.js.map +1 -1
- package/dist/gs/crypto/sha256/index.d.ts +8 -0
- package/dist/gs/crypto/sha256/index.js +118 -0
- package/dist/gs/crypto/sha256/index.js.map +1 -0
- package/dist/gs/crypto/sha512/index.d.ts +14 -0
- package/dist/gs/crypto/sha512/index.js +129 -0
- package/dist/gs/crypto/sha512/index.js.map +1 -0
- package/dist/gs/embed/index.d.ts +7 -0
- package/dist/gs/embed/index.js +16 -0
- package/dist/gs/embed/index.js.map +1 -0
- package/dist/gs/encoding/json/index.d.ts +4 -0
- package/dist/gs/encoding/json/index.js +33 -0
- package/dist/gs/encoding/json/index.js.map +1 -1
- package/dist/gs/errors/errors.d.ts +4 -0
- package/dist/gs/errors/errors.js +108 -4
- package/dist/gs/errors/errors.js.map +1 -1
- package/dist/gs/fmt/fmt.d.ts +4 -4
- package/dist/gs/fmt/fmt.js +42 -11
- package/dist/gs/fmt/fmt.js.map +1 -1
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/index.d.ts +37 -2
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/index.js +245 -1
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/index.js.map +1 -1
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/json/index.d.ts +189 -0
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/json/index.js +861 -0
- package/dist/gs/github.com/aperturerobotics/protobuf-go-lite/json/index.js.map +1 -0
- package/dist/gs/github.com/aperturerobotics/starpc/srpc/index.d.ts +217 -0
- package/dist/gs/github.com/aperturerobotics/starpc/srpc/index.js +814 -0
- package/dist/gs/github.com/aperturerobotics/starpc/srpc/index.js.map +1 -0
- package/dist/gs/github.com/aperturerobotics/util/conc/index.d.ts +20 -0
- package/dist/gs/github.com/aperturerobotics/util/conc/index.js +134 -0
- package/dist/gs/github.com/aperturerobotics/util/conc/index.js.map +1 -0
- package/dist/gs/github.com/aperturerobotics/wasivm/wazero/kernel/runtime/browser/browser.js.map +1 -1
- package/dist/gs/github.com/hack-pad/safejs/internal/catch/index.d.ts +3 -0
- package/dist/gs/github.com/hack-pad/safejs/internal/catch/index.js +50 -0
- package/dist/gs/github.com/hack-pad/safejs/internal/catch/index.js.map +1 -0
- package/dist/gs/github.com/klauspost/compress/internal/le/index.d.ts +9 -0
- package/dist/gs/github.com/klauspost/compress/internal/le/index.js +72 -0
- package/dist/gs/github.com/klauspost/compress/internal/le/index.js.map +1 -0
- package/dist/gs/github.com/mr-tron/base58/base58/index.d.ts +27 -0
- package/dist/gs/github.com/mr-tron/base58/base58/index.js +172 -0
- package/dist/gs/github.com/mr-tron/base58/base58/index.js.map +1 -0
- package/dist/gs/github.com/zeebo/blake3/internal/consts/index.d.ts +21 -0
- package/dist/gs/github.com/zeebo/blake3/internal/consts/index.js +22 -0
- package/dist/gs/github.com/zeebo/blake3/internal/consts/index.js.map +1 -0
- package/dist/gs/go/internal/scannerhooks/index.d.ts +3 -0
- package/dist/gs/go/internal/scannerhooks/index.js +5 -0
- package/dist/gs/go/internal/scannerhooks/index.js.map +1 -0
- package/dist/gs/go/scanner/index.d.ts +13 -0
- package/dist/gs/go/scanner/index.js +35 -0
- package/dist/gs/go/scanner/index.js.map +1 -1
- package/dist/gs/go/token/index.d.ts +156 -0
- package/dist/gs/go/token/index.js +507 -4
- package/dist/gs/go/token/index.js.map +1 -1
- package/dist/gs/hash/fnv/index.d.ts +57 -0
- package/dist/gs/hash/fnv/index.js +299 -0
- package/dist/gs/hash/fnv/index.js.map +1 -0
- package/dist/gs/hash/index.d.ts +17 -0
- package/dist/gs/hash/index.js +94 -0
- package/dist/gs/hash/index.js.map +1 -0
- package/dist/gs/internal/abi/index.d.ts +4 -0
- package/dist/gs/internal/abi/index.js +10 -0
- package/dist/gs/internal/abi/index.js.map +1 -1
- package/dist/gs/internal/bytealg/index.d.ts +2 -0
- package/dist/gs/internal/bytealg/index.js +14 -0
- package/dist/gs/internal/bytealg/index.js.map +1 -1
- package/dist/gs/internal/byteorder/index.d.ts +8 -2
- package/dist/gs/internal/byteorder/index.js +56 -25
- package/dist/gs/internal/byteorder/index.js.map +1 -1
- package/dist/gs/internal/godebug/index.d.ts +12 -0
- package/dist/gs/internal/godebug/index.js +30 -0
- package/dist/gs/internal/godebug/index.js.map +1 -0
- package/dist/gs/io/fs/index.d.ts +1 -0
- package/dist/gs/io/fs/index.js +1 -0
- package/dist/gs/io/fs/index.js.map +1 -1
- package/dist/gs/io/fs/readlink.d.ts +8 -0
- package/dist/gs/io/fs/readlink.js +60 -0
- package/dist/gs/io/fs/readlink.js.map +1 -0
- package/dist/gs/io/fs/walk.d.ts +3 -3
- package/dist/gs/io/fs/walk.js +7 -7
- package/dist/gs/io/fs/walk.js.map +1 -1
- package/dist/gs/io/io.d.ts +40 -6
- package/dist/gs/io/io.js +151 -26
- package/dist/gs/io/io.js.map +1 -1
- package/dist/gs/iter/iter.d.ts +3 -2
- package/dist/gs/iter/iter.js.map +1 -1
- package/dist/gs/maps/iter.d.ts +5 -5
- package/dist/gs/maps/iter.js +48 -21
- package/dist/gs/maps/iter.js.map +1 -1
- package/dist/gs/maps/maps.d.ts +6 -6
- package/dist/gs/maps/maps.js +1 -1
- package/dist/gs/maps/maps.js.map +1 -1
- package/dist/gs/math/bits/index.d.ts +13 -4
- package/dist/gs/math/bits/index.js +70 -48
- package/dist/gs/math/bits/index.js.map +1 -1
- package/dist/gs/math/const.gs.d.ts +5 -5
- package/dist/gs/math/const.gs.js +4 -4
- package/dist/gs/math/const.gs.js.map +1 -1
- package/dist/gs/mime/index.d.ts +1 -0
- package/dist/gs/mime/index.js +52 -0
- package/dist/gs/mime/index.js.map +1 -0
- package/dist/gs/net/http/httptest/index.d.ts +30 -0
- package/dist/gs/net/http/httptest/index.js +101 -0
- package/dist/gs/net/http/httptest/index.js.map +1 -0
- package/dist/gs/net/http/index.d.ts +131 -0
- package/dist/gs/net/http/index.js +307 -0
- package/dist/gs/net/http/index.js.map +1 -0
- package/dist/gs/net/http/pprof/index.d.ts +8 -0
- package/dist/gs/net/http/pprof/index.js +59 -0
- package/dist/gs/net/http/pprof/index.js.map +1 -0
- package/dist/gs/os/dir_unix.gs.js +2 -2
- package/dist/gs/os/dir_unix.gs.js.map +1 -1
- package/dist/gs/os/error.gs.js +9 -7
- package/dist/gs/os/error.gs.js.map +1 -1
- package/dist/gs/os/types_js.gs.js +95 -15
- package/dist/gs/os/types_js.gs.js.map +1 -1
- package/dist/gs/path/filepath/match.js +165 -3
- package/dist/gs/path/filepath/match.js.map +1 -1
- package/dist/gs/path/filepath/path.d.ts +8 -4
- package/dist/gs/path/filepath/path.js +192 -8
- package/dist/gs/path/filepath/path.js.map +1 -1
- package/dist/gs/path/path.d.ts +4 -1
- package/dist/gs/path/path.js +16 -4
- package/dist/gs/path/path.js.map +1 -1
- package/dist/gs/reflect/index.d.ts +4 -3
- package/dist/gs/reflect/index.js +3 -2
- package/dist/gs/reflect/index.js.map +1 -1
- package/dist/gs/reflect/iter.js +2 -2
- package/dist/gs/reflect/iter.js.map +1 -1
- package/dist/gs/reflect/map.js +29 -0
- package/dist/gs/reflect/map.js.map +1 -1
- package/dist/gs/reflect/type.d.ts +31 -9
- package/dist/gs/reflect/type.js +536 -43
- package/dist/gs/reflect/type.js.map +1 -1
- package/dist/gs/reflect/types.d.ts +1 -0
- package/dist/gs/reflect/types.js +3 -1
- package/dist/gs/reflect/types.js.map +1 -1
- package/dist/gs/reflect/value.d.ts +4 -1
- package/dist/gs/reflect/value.js +39 -1
- package/dist/gs/reflect/value.js.map +1 -1
- package/dist/gs/reflect/visiblefields.js +1 -1
- package/dist/gs/reflect/visiblefields.js.map +1 -1
- package/dist/gs/runtime/debug/index.d.ts +41 -0
- package/dist/gs/runtime/debug/index.js +66 -0
- package/dist/gs/runtime/debug/index.js.map +1 -0
- package/dist/gs/runtime/pprof/index.d.ts +20 -0
- package/dist/gs/runtime/pprof/index.js +85 -0
- package/dist/gs/runtime/pprof/index.js.map +1 -0
- package/dist/gs/runtime/runtime.d.ts +35 -3
- package/dist/gs/runtime/runtime.js +72 -0
- package/dist/gs/runtime/runtime.js.map +1 -1
- package/dist/gs/runtime/trace/index.d.ts +19 -0
- package/dist/gs/runtime/trace/index.js +64 -0
- package/dist/gs/runtime/trace/index.js.map +1 -0
- package/dist/gs/slices/slices.d.ts +42 -8
- package/dist/gs/slices/slices.js +425 -11
- package/dist/gs/slices/slices.js.map +1 -1
- package/dist/gs/sort/slice.gs.d.ts +5 -3
- package/dist/gs/sort/slice.gs.js +60 -22
- package/dist/gs/sort/slice.gs.js.map +1 -1
- package/dist/gs/sort/sort.gs.d.ts +4 -4
- package/dist/gs/sort/sort.gs.js +11 -8
- package/dist/gs/sort/sort.gs.js.map +1 -1
- package/dist/gs/strings/builder.d.ts +1 -1
- package/dist/gs/strings/builder.js +29 -19
- package/dist/gs/strings/builder.js.map +1 -1
- package/dist/gs/strings/iter.js +140 -75
- package/dist/gs/strings/iter.js.map +1 -1
- package/dist/gs/strings/replace.js +2 -2
- package/dist/gs/strings/replace.js.map +1 -1
- package/dist/gs/strings/strings.js +52 -6
- package/dist/gs/strings/strings.js.map +1 -1
- package/dist/gs/sync/atomic/type.gs.d.ts +9 -8
- package/dist/gs/sync/atomic/type.gs.js +0 -2
- package/dist/gs/sync/atomic/type.gs.js.map +1 -1
- package/dist/gs/sync/sync.d.ts +8 -3
- package/dist/gs/sync/sync.js +66 -11
- package/dist/gs/sync/sync.js.map +1 -1
- package/dist/gs/syscall/constants.d.ts +36 -24
- package/dist/gs/syscall/constants.js +12 -0
- package/dist/gs/syscall/constants.js.map +1 -1
- package/dist/gs/syscall/errors.d.ts +117 -111
- package/dist/gs/syscall/errors.js +45 -0
- package/dist/gs/syscall/errors.js.map +1 -1
- package/dist/gs/syscall/fs.d.ts +37 -0
- package/dist/gs/syscall/fs.js +102 -0
- package/dist/gs/syscall/fs.js.map +1 -1
- package/dist/gs/syscall/js/index.d.ts +90 -0
- package/dist/gs/syscall/js/index.js +383 -0
- package/dist/gs/syscall/js/index.js.map +1 -0
- package/dist/gs/syscall/types.d.ts +26 -1
- package/dist/gs/syscall/types.js +45 -1
- package/dist/gs/syscall/types.js.map +1 -1
- package/dist/gs/testing/index.d.ts +1 -0
- package/dist/gs/testing/index.js +2 -0
- package/dist/gs/testing/index.js.map +1 -0
- package/dist/gs/testing/testing.d.ts +78 -0
- package/dist/gs/testing/testing.js +318 -0
- package/dist/gs/testing/testing.js.map +1 -0
- package/dist/gs/time/time.d.ts +41 -4
- package/dist/gs/time/time.js +227 -36
- package/dist/gs/time/time.js.map +1 -1
- package/dist/gs/unicode/unicode.d.ts +23 -1
- package/dist/gs/unicode/unicode.js +79 -10
- package/dist/gs/unicode/unicode.js.map +1 -1
- package/dist/gs/unicode/utf8/utf8.d.ts +4 -4
- package/dist/gs/unicode/utf8/utf8.js +24 -11
- package/dist/gs/unicode/utf8/utf8.js.map +1 -1
- package/dist/gs/unique/index.d.ts +11 -0
- package/dist/gs/unique/index.js +76 -0
- package/dist/gs/unique/index.js.map +1 -0
- package/go.mod +8 -8
- package/go.sum +14 -14
- package/gs/builtin/builtin.ts +585 -27
- package/gs/builtin/channel.ts +183 -29
- package/gs/builtin/defer.ts +13 -2
- package/gs/builtin/hostio.test.ts +1 -0
- package/gs/builtin/hostio.ts +38 -0
- package/gs/builtin/map.ts +46 -6
- package/gs/builtin/print.ts +12 -3
- package/gs/builtin/runtime-contract.test.ts +383 -10
- package/gs/builtin/slice.test.ts +70 -0
- package/gs/builtin/slice.ts +785 -265
- package/gs/builtin/type.ts +160 -41
- package/gs/builtin/varRef.ts +40 -1
- package/gs/bytes/buffer.gs.ts +74 -70
- package/gs/bytes/iter.gs.ts +13 -14
- package/gs/bytes/meta.json +8 -3
- package/gs/bytes/reader.gs.ts +20 -19
- package/gs/compress/zlib/index.test.ts +28 -0
- package/gs/compress/zlib/index.ts +200 -0
- package/gs/compress/zlib/meta.json +3 -0
- package/gs/context/context.test.ts +71 -0
- package/gs/context/context.ts +30 -29
- package/gs/crypto/ecdh/index.test.ts +43 -0
- package/gs/crypto/ecdh/index.ts +274 -0
- package/gs/crypto/ed25519/index.test.ts +41 -0
- package/gs/crypto/ed25519/index.ts +238 -0
- package/gs/crypto/ed25519/meta.json +13 -0
- package/gs/crypto/internal/constanttime/index.test.ts +25 -0
- package/gs/crypto/internal/constanttime/index.ts +22 -0
- package/gs/crypto/internal/fips140deps/byteorder/index.ts +1 -0
- package/gs/crypto/internal/fips140deps/godebug/index.ts +1 -0
- package/gs/crypto/rand/index.test.ts +89 -1
- package/gs/crypto/rand/index.ts +103 -1
- package/gs/crypto/rand/meta.json +4 -1
- package/gs/crypto/sha256/index.test.ts +78 -0
- package/gs/crypto/sha256/index.ts +150 -0
- package/gs/crypto/sha256/meta.json +9 -0
- package/gs/crypto/sha512/index.test.ts +31 -0
- package/gs/crypto/sha512/index.ts +161 -0
- package/gs/crypto/sha512/meta.json +11 -0
- package/gs/embed/index.ts +20 -0
- package/gs/embed/meta.json +5 -0
- package/gs/encoding/json/index.test.ts +39 -3
- package/gs/encoding/json/index.ts +45 -3
- package/gs/errors/errors.test.ts +85 -0
- package/gs/errors/errors.ts +132 -4
- package/gs/fmt/fmt.test.ts +3 -1
- package/gs/fmt/fmt.ts +55 -19
- package/gs/github.com/aperturerobotics/protobuf-go-lite/index.test.ts +128 -1
- package/gs/github.com/aperturerobotics/protobuf-go-lite/index.ts +342 -4
- package/gs/github.com/aperturerobotics/protobuf-go-lite/json/index.test.ts +180 -0
- package/gs/github.com/aperturerobotics/protobuf-go-lite/json/index.ts +1084 -0
- package/gs/github.com/aperturerobotics/starpc/srpc/index.test.ts +31 -0
- package/gs/github.com/aperturerobotics/starpc/srpc/index.ts +1233 -0
- package/gs/github.com/aperturerobotics/starpc/srpc/meta.json +46 -0
- package/gs/github.com/aperturerobotics/util/conc/index.test.ts +30 -0
- package/gs/github.com/aperturerobotics/util/conc/index.ts +172 -0
- package/gs/github.com/aperturerobotics/util/conc/meta.json +9 -0
- package/gs/github.com/aperturerobotics/wasivm/wazero/kernel/runtime/browser/browser.ts +1 -4
- package/gs/github.com/hack-pad/safejs/internal/catch/index.test.ts +35 -0
- package/gs/github.com/hack-pad/safejs/internal/catch/index.ts +65 -0
- package/gs/github.com/hack-pad/safejs/internal/catch/meta.json +9 -0
- package/gs/github.com/klauspost/compress/internal/le/index.test.ts +37 -0
- package/gs/github.com/klauspost/compress/internal/le/index.ts +115 -0
- package/gs/github.com/mr-tron/base58/base58/index.test.ts +70 -0
- package/gs/github.com/mr-tron/base58/base58/index.ts +231 -0
- package/gs/github.com/mr-tron/base58/base58/meta.json +3 -0
- package/gs/github.com/zeebo/blake3/internal/consts/index.test.ts +46 -0
- package/gs/github.com/zeebo/blake3/internal/consts/index.ts +26 -0
- package/gs/go/internal/scannerhooks/index.test.ts +14 -0
- package/gs/go/internal/scannerhooks/index.ts +9 -0
- package/gs/go/scanner/index.test.ts +22 -0
- package/gs/go/scanner/index.ts +47 -0
- package/gs/go/token/index.test.ts +47 -1
- package/gs/go/token/index.ts +583 -4
- package/gs/hash/fnv/index.test.ts +67 -0
- package/gs/hash/fnv/index.ts +351 -0
- package/gs/hash/fnv/meta.json +3 -0
- package/gs/hash/index.test.ts +37 -0
- package/gs/hash/index.ts +118 -0
- package/gs/hash/meta.json +5 -0
- package/gs/internal/abi/index.test.ts +18 -0
- package/gs/internal/abi/index.ts +14 -0
- package/gs/internal/bytealg/index.test.ts +18 -0
- package/gs/internal/bytealg/index.ts +16 -0
- package/gs/internal/byteorder/index.test.ts +39 -0
- package/gs/internal/byteorder/index.ts +100 -27
- package/gs/internal/godebug/index.test.ts +16 -0
- package/gs/internal/godebug/index.ts +35 -0
- package/gs/io/fs/index.ts +1 -0
- package/gs/io/fs/meta.json +5 -0
- package/gs/io/fs/readlink.test.ts +43 -0
- package/gs/io/fs/readlink.ts +69 -0
- package/gs/io/fs/walk.test.ts +61 -0
- package/gs/io/fs/walk.ts +17 -9
- package/gs/io/io.ts +177 -31
- package/gs/io/meta.json +10 -2
- package/gs/iter/iter.ts +8 -2
- package/gs/maps/iter.ts +75 -26
- package/gs/maps/maps.test.ts +23 -0
- package/gs/maps/maps.ts +13 -11
- package/gs/math/bits/index.test.ts +20 -0
- package/gs/math/bits/index.ts +107 -64
- package/gs/math/const.gs.test.ts +11 -5
- package/gs/math/const.gs.ts +5 -6
- package/gs/mime/index.ts +60 -0
- package/gs/net/http/httptest/index.test.ts +53 -0
- package/gs/net/http/httptest/index.ts +120 -0
- package/gs/net/http/index.test.ts +148 -0
- package/gs/net/http/index.ts +432 -0
- package/gs/net/http/meta.json +6 -0
- package/gs/net/http/pprof/index.test.ts +47 -0
- package/gs/net/http/pprof/index.ts +65 -0
- package/gs/os/dir_unix.gs.ts +2 -3
- package/gs/os/error.gs.ts +9 -10
- package/gs/os/error.test.ts +41 -0
- package/gs/os/file_unix_js.test.ts +55 -0
- package/gs/os/tempfile.gs.test.ts +37 -10
- package/gs/os/types_js.gs.ts +96 -17
- package/gs/path/filepath/match.test.ts +31 -12
- package/gs/path/filepath/match.ts +181 -3
- package/gs/path/filepath/meta.json +6 -0
- package/gs/path/filepath/path.test.ts +80 -0
- package/gs/path/filepath/path.ts +244 -11
- package/gs/path/path.ts +20 -5
- package/gs/reflect/field.test.ts +63 -0
- package/gs/reflect/index.ts +5 -1
- package/gs/reflect/iter.ts +2 -2
- package/gs/reflect/map.test.ts +42 -1
- package/gs/reflect/map.ts +39 -0
- package/gs/reflect/type.ts +728 -65
- package/gs/reflect/typefor.test.ts +100 -0
- package/gs/reflect/types.ts +3 -1
- package/gs/reflect/value.ts +50 -1
- package/gs/reflect/visiblefields.ts +1 -1
- package/gs/runtime/debug/index.test.ts +45 -0
- package/gs/runtime/debug/index.ts +96 -0
- package/gs/runtime/pprof/index.test.ts +36 -0
- package/gs/runtime/pprof/index.ts +104 -0
- package/gs/runtime/pprof/meta.json +6 -0
- package/gs/runtime/runtime.test.ts +19 -0
- package/gs/runtime/runtime.ts +98 -3
- package/gs/runtime/trace/index.test.ts +45 -0
- package/gs/runtime/trace/index.ts +97 -0
- package/gs/runtime/trace/meta.json +7 -0
- package/gs/slices/meta.json +2 -1
- package/gs/slices/slices.test.ts +180 -0
- package/gs/slices/slices.ts +502 -15
- package/gs/sort/meta.json +7 -0
- package/gs/sort/slice.gs.ts +85 -26
- package/gs/sort/slice.test.ts +40 -0
- package/gs/sort/sort.gs.ts +16 -13
- package/gs/strings/builder.test.ts +8 -0
- package/gs/strings/builder.ts +33 -20
- package/gs/strings/iter.test.ts +5 -7
- package/gs/strings/iter.ts +146 -71
- package/gs/strings/replace.test.ts +1 -4
- package/gs/strings/replace.ts +6 -6
- package/gs/strings/strings.test.ts +4 -0
- package/gs/strings/strings.ts +54 -6
- package/gs/sync/atomic/type.gs.ts +13 -14
- package/gs/sync/meta.json +3 -1
- package/gs/sync/sync.test.ts +69 -1
- package/gs/sync/sync.ts +72 -13
- package/gs/syscall/constants.ts +39 -24
- package/gs/syscall/errors.ts +165 -112
- package/gs/syscall/fs.ts +195 -0
- package/gs/syscall/js/index.ts +485 -0
- package/gs/syscall/js/meta.json +4 -0
- package/gs/syscall/net.test.ts +111 -0
- package/gs/syscall/types.ts +63 -2
- package/gs/testing/index.ts +1 -0
- package/gs/testing/meta.json +5 -0
- package/gs/testing/testing.test.ts +146 -0
- package/gs/testing/testing.ts +399 -0
- package/gs/time/meta.json +2 -2
- package/gs/time/time.test.ts +110 -0
- package/gs/time/time.ts +309 -57
- package/gs/unicode/unicode.test.ts +36 -0
- package/gs/unicode/unicode.ts +115 -9
- package/gs/unicode/utf8/utf8.test.ts +13 -0
- package/gs/unicode/utf8/utf8.ts +28 -16
- package/gs/unique/index.ts +98 -0
- package/package.json +3 -2
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest'
|
|
2
|
+
|
|
3
|
+
import { varRef } from '../../builtin/varRef.js'
|
|
4
|
+
import {
|
|
5
|
+
Client,
|
|
6
|
+
DefaultTransport,
|
|
7
|
+
File,
|
|
8
|
+
FileSystem,
|
|
9
|
+
Header,
|
|
10
|
+
Header_Set,
|
|
11
|
+
HandlerFunc_ServeHTTP,
|
|
12
|
+
Get,
|
|
13
|
+
MethodPost,
|
|
14
|
+
MethodDelete,
|
|
15
|
+
NewRequest,
|
|
16
|
+
NotFound,
|
|
17
|
+
ParseTime,
|
|
18
|
+
Response,
|
|
19
|
+
ResponseWriter,
|
|
20
|
+
Server,
|
|
21
|
+
StatusCreated,
|
|
22
|
+
StatusNotFound,
|
|
23
|
+
StatusOK,
|
|
24
|
+
StatusServiceUnavailable,
|
|
25
|
+
StatusText,
|
|
26
|
+
StatusTooManyRequests,
|
|
27
|
+
} from './index.js'
|
|
28
|
+
|
|
29
|
+
describe('net/http override', () => {
|
|
30
|
+
it('exports response status helpers', () => {
|
|
31
|
+
const resp = new Response({ StatusCode: StatusOK })
|
|
32
|
+
|
|
33
|
+
expect(resp.StatusCode).toBe(200)
|
|
34
|
+
expect(StatusText(resp.StatusCode)).toBe('OK')
|
|
35
|
+
expect(StatusText(StatusNotFound)).toBe('Not Found')
|
|
36
|
+
expect(StatusText(StatusTooManyRequests)).toBe('Too Many Requests')
|
|
37
|
+
expect(StatusText(StatusServiceUnavailable)).toBe('Service Unavailable')
|
|
38
|
+
expect(StatusText(599)).toBe('')
|
|
39
|
+
expect(MethodPost).toBe('POST')
|
|
40
|
+
expect(MethodDelete).toBe('DELETE')
|
|
41
|
+
expect(StatusCreated).toBe(201)
|
|
42
|
+
})
|
|
43
|
+
|
|
44
|
+
it('returns an explicit unsupported error for Get', () => {
|
|
45
|
+
const [resp, err] = Get('https://example.invalid')
|
|
46
|
+
|
|
47
|
+
expect(resp).toBeNull()
|
|
48
|
+
expect(err?.Error()).toBe('net/http: Get is not implemented in GoScript')
|
|
49
|
+
})
|
|
50
|
+
|
|
51
|
+
it('accepts VarRef requests for client calls', async () => {
|
|
52
|
+
const [req, reqErr] = NewRequest(MethodPost, 'https://example.invalid', null)
|
|
53
|
+
expect(reqErr).toBeNull()
|
|
54
|
+
expect((req!.URL as any).Path).toBe('/')
|
|
55
|
+
expect(req!.RequestURI).toBe('/')
|
|
56
|
+
|
|
57
|
+
const [resp, err] = await new Client().Do(varRef(req!))
|
|
58
|
+
expect(resp).toBeNull()
|
|
59
|
+
expect(err?.Error()).toBe('net/http: Client.Do is not implemented in GoScript')
|
|
60
|
+
})
|
|
61
|
+
|
|
62
|
+
it('exports the default transport surface', async () => {
|
|
63
|
+
const [req] = NewRequest(MethodPost, 'https://example.invalid', null)
|
|
64
|
+
|
|
65
|
+
const [resp, err] = await DefaultTransport.RoundTrip(req)
|
|
66
|
+
|
|
67
|
+
expect(resp).toBeNull()
|
|
68
|
+
expect(err?.Error()).toBe('net/http: Client.Do is not implemented in GoScript')
|
|
69
|
+
})
|
|
70
|
+
|
|
71
|
+
it('delegates client calls through RoundTripper implementations', async () => {
|
|
72
|
+
const [req] = NewRequest(MethodPost, 'https://example.invalid/path', null)
|
|
73
|
+
Header_Set(req!.Header, 'User-Agent', 'goscript-test')
|
|
74
|
+
req!.RemoteAddr = '127.0.0.1:1234'
|
|
75
|
+
req!.ContentLength = 42
|
|
76
|
+
|
|
77
|
+
const client = new Client({
|
|
78
|
+
Transport: {
|
|
79
|
+
RoundTrip: (got) => {
|
|
80
|
+
const request = (got as any).value ?? got
|
|
81
|
+
expect(request.UserAgent()).toBe('goscript-test')
|
|
82
|
+
expect(request.RemoteAddr).toBe('127.0.0.1:1234')
|
|
83
|
+
expect(request.RequestURI).toBe('/path')
|
|
84
|
+
expect(request.ContentLength).toBe(42)
|
|
85
|
+
return [new Response({ StatusCode: StatusOK }), null]
|
|
86
|
+
},
|
|
87
|
+
},
|
|
88
|
+
})
|
|
89
|
+
|
|
90
|
+
const [resp, err] = await client.Do(varRef(req!))
|
|
91
|
+
expect(err).toBeNull()
|
|
92
|
+
expect(resp?.StatusCode).toBe(StatusOK)
|
|
93
|
+
})
|
|
94
|
+
|
|
95
|
+
it('accepts server context and shutdown surfaces', () => {
|
|
96
|
+
const srv = new Server({
|
|
97
|
+
Addr: ':0',
|
|
98
|
+
BaseContext: () => ({} as any),
|
|
99
|
+
ReadHeaderTimeout: 10,
|
|
100
|
+
})
|
|
101
|
+
|
|
102
|
+
expect(srv.Addr).toBe(':0')
|
|
103
|
+
expect(srv.BaseContext?.(null)).toEqual({})
|
|
104
|
+
expect(srv.ReadHeaderTimeout).toBe(10)
|
|
105
|
+
expect(srv.Shutdown({} as any)).toBeNull()
|
|
106
|
+
expect(srv.ListenAndServeTLS('cert.pem', 'key.pem')?.Error()).toBe('net/http: Server.ListenAndServeTLS is not implemented in GoScript')
|
|
107
|
+
})
|
|
108
|
+
|
|
109
|
+
it('supports handler functions and not-found responses for typechecked server tests', () => {
|
|
110
|
+
const writes: string[] = []
|
|
111
|
+
const writer: ResponseWriter = {
|
|
112
|
+
Header: () => new Header(),
|
|
113
|
+
Write: (p) => {
|
|
114
|
+
writes.push(Buffer.from(p ?? []).toString('utf8'))
|
|
115
|
+
return [p?.length ?? 0, null]
|
|
116
|
+
},
|
|
117
|
+
WriteHeader: (code) => writes.push(`status:${code}`),
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
HandlerFunc_ServeHTTP((_w, _r) => undefined, writer, null)
|
|
121
|
+
NotFound(writer, null)
|
|
122
|
+
|
|
123
|
+
expect(writes).toEqual(['status:404', '404 page not found\n'])
|
|
124
|
+
})
|
|
125
|
+
|
|
126
|
+
it('parses HTTP dates', () => {
|
|
127
|
+
const [parsed, err] = ParseTime('Sun, 06 Nov 1994 08:49:37 GMT')
|
|
128
|
+
|
|
129
|
+
expect(err).toBeNull()
|
|
130
|
+
expect(parsed.Unix()).toBe(784111777)
|
|
131
|
+
})
|
|
132
|
+
|
|
133
|
+
it('exports file server interface shapes', () => {
|
|
134
|
+
const file: File = {
|
|
135
|
+
Close: () => null,
|
|
136
|
+
Read: (p) => [p?.length ?? 0, null],
|
|
137
|
+
Seek: (offset) => [offset, null],
|
|
138
|
+
Readdir: () => [null, null],
|
|
139
|
+
Stat: () => [null, null],
|
|
140
|
+
}
|
|
141
|
+
const fsys: FileSystem = {
|
|
142
|
+
Open: (name) => (name === 'ok' ? [file, null] : [null, new Error('missing')]),
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
expect(fsys.Open('ok')[0]).toBe(file)
|
|
146
|
+
expect(fsys.Open('missing')[1]?.message).toBe('missing')
|
|
147
|
+
})
|
|
148
|
+
})
|
|
@@ -0,0 +1,432 @@
|
|
|
1
|
+
import * as $ from '@goscript/builtin/index.js'
|
|
2
|
+
import * as context from '@goscript/context/index.js'
|
|
3
|
+
import * as errors from '@goscript/errors/index.js'
|
|
4
|
+
import * as fs from '@goscript/io/fs/fs.js'
|
|
5
|
+
import * as io from '@goscript/io/index.js'
|
|
6
|
+
import * as time from '@goscript/time/index.js'
|
|
7
|
+
|
|
8
|
+
export const StatusOK = 200
|
|
9
|
+
export const StatusCreated = 201
|
|
10
|
+
export const StatusPartialContent = 206
|
|
11
|
+
export const StatusMovedPermanently = 301
|
|
12
|
+
export const StatusBadRequest = 400
|
|
13
|
+
export const StatusRequestTimeout = 408
|
|
14
|
+
export const StatusConflict = 409
|
|
15
|
+
export const StatusNotFound = 404
|
|
16
|
+
export const StatusTooManyRequests = 429
|
|
17
|
+
export const StatusRequestedRangeNotSatisfiable = 416
|
|
18
|
+
export const StatusInternalServerError = 500
|
|
19
|
+
export const StatusServiceUnavailable = 503
|
|
20
|
+
|
|
21
|
+
export const MethodGet = 'GET'
|
|
22
|
+
export const MethodPost = 'POST'
|
|
23
|
+
export const MethodDelete = 'DELETE'
|
|
24
|
+
|
|
25
|
+
export const ErrNotSupported = errors.New('feature not supported')
|
|
26
|
+
export const ServerContextKey = Symbol('net/http ServerContextKey')
|
|
27
|
+
|
|
28
|
+
export function StatusText(code: number): string {
|
|
29
|
+
switch (code) {
|
|
30
|
+
case StatusOK:
|
|
31
|
+
return 'OK'
|
|
32
|
+
case StatusMovedPermanently:
|
|
33
|
+
return 'Moved Permanently'
|
|
34
|
+
case StatusBadRequest:
|
|
35
|
+
return 'Bad Request'
|
|
36
|
+
case StatusRequestTimeout:
|
|
37
|
+
return 'Request Timeout'
|
|
38
|
+
case StatusConflict:
|
|
39
|
+
return 'Conflict'
|
|
40
|
+
case StatusNotFound:
|
|
41
|
+
return 'Not Found'
|
|
42
|
+
case StatusTooManyRequests:
|
|
43
|
+
return 'Too Many Requests'
|
|
44
|
+
case StatusPartialContent:
|
|
45
|
+
return 'Partial Content'
|
|
46
|
+
case StatusRequestedRangeNotSatisfiable:
|
|
47
|
+
return 'Requested Range Not Satisfiable'
|
|
48
|
+
case StatusInternalServerError:
|
|
49
|
+
return 'Internal Server Error'
|
|
50
|
+
case StatusServiceUnavailable:
|
|
51
|
+
return 'Service Unavailable'
|
|
52
|
+
default:
|
|
53
|
+
return ''
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
export type Header = Map<string, $.Slice<string>>
|
|
58
|
+
|
|
59
|
+
export const Header = Map as {
|
|
60
|
+
new(entries?: Iterable<readonly [string, $.Slice<string>]> | null): Header
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
export function Header_Add(h: Header, key: string, value: string): void {
|
|
64
|
+
const values = Array.from(h.get(key) ?? [])
|
|
65
|
+
values.push(value)
|
|
66
|
+
h.set(key, $.arrayToSlice(values))
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
export function Header_Del(h: Header, key: string): void {
|
|
70
|
+
h.delete(key)
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
export function Header_Get(h: Header, key: string): string {
|
|
74
|
+
const values = h.get(key)
|
|
75
|
+
return values == null || values.length === 0 ? '' : String(values[0])
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
export function Header_Set(h: Header, key: string, value: string): void {
|
|
79
|
+
h.set(key, $.arrayToSlice([value]))
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
class QueryValues extends Map<string, $.Slice<string>> {
|
|
83
|
+
public Add(key: string, value: string): void {
|
|
84
|
+
const values = Array.from(this.get(key) ?? [])
|
|
85
|
+
values.push(value)
|
|
86
|
+
this.set(key, $.arrayToSlice(values))
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
public Get(key: string): string {
|
|
90
|
+
const values = this.get(key)
|
|
91
|
+
return values == null || values.length === 0 ? '' : String(values[0])
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
class RequestURL {
|
|
96
|
+
public Path: string
|
|
97
|
+
public RawQuery: string
|
|
98
|
+
|
|
99
|
+
constructor(path: string, rawQuery: string) {
|
|
100
|
+
this.Path = path
|
|
101
|
+
this.RawQuery = rawQuery
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
public Query(): QueryValues {
|
|
105
|
+
const values = new QueryValues()
|
|
106
|
+
const params = new URLSearchParams(this.RawQuery)
|
|
107
|
+
params.forEach((value, key) => values.Add(key, value))
|
|
108
|
+
return values
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
public clone(): RequestURL {
|
|
112
|
+
return new RequestURL(this.Path, this.RawQuery)
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
function parseRequestURL(rawURL: string): RequestURL {
|
|
117
|
+
try {
|
|
118
|
+
const parsed = new URL(rawURL, 'http://goscript.invalid')
|
|
119
|
+
return new RequestURL(parsed.pathname, parsed.search.startsWith('?') ? parsed.search.slice(1) : parsed.search)
|
|
120
|
+
} catch {
|
|
121
|
+
return new RequestURL('', '')
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
export interface ResponseWriter {
|
|
126
|
+
Header(): Header
|
|
127
|
+
Write(p: $.Slice<number>): [number, $.GoError]
|
|
128
|
+
WriteHeader(statusCode: number): void
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
export class Request {
|
|
132
|
+
public Method: string
|
|
133
|
+
public URL: any
|
|
134
|
+
public Body: io.Reader | null
|
|
135
|
+
public Header: Header
|
|
136
|
+
public ContentLength: number
|
|
137
|
+
public RequestURI: string
|
|
138
|
+
public RemoteAddr: string
|
|
139
|
+
private ctx: context.Context
|
|
140
|
+
|
|
141
|
+
constructor(init?: Partial<Request> & { ctx?: context.Context }) {
|
|
142
|
+
this.Method = init?.Method ?? ''
|
|
143
|
+
this.URL = init?.URL ?? null
|
|
144
|
+
this.Body = init?.Body ?? null
|
|
145
|
+
this.Header = init?.Header ?? new Header()
|
|
146
|
+
this.ContentLength = init?.ContentLength ?? 0
|
|
147
|
+
this.RequestURI = init?.RequestURI ?? ''
|
|
148
|
+
this.RemoteAddr = init?.RemoteAddr ?? ''
|
|
149
|
+
this.ctx = (init as { ctx?: context.Context } | undefined)?.ctx ?? context.Background()
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
public Context(): context.Context {
|
|
153
|
+
return this.ctx
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
public WithContext(ctx: context.Context): Request {
|
|
157
|
+
return this.Clone(ctx)
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
public Clone(ctx: context.Context): Request {
|
|
161
|
+
return new Request({
|
|
162
|
+
Method: this.Method,
|
|
163
|
+
URL: this.URL?.clone != null ? this.URL.clone() : this.URL == null ? null : { ...this.URL },
|
|
164
|
+
Body: this.Body,
|
|
165
|
+
Header: this.Header,
|
|
166
|
+
ContentLength: this.ContentLength,
|
|
167
|
+
RequestURI: this.RequestURI,
|
|
168
|
+
RemoteAddr: this.RemoteAddr,
|
|
169
|
+
ctx,
|
|
170
|
+
})
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
public UserAgent(): string {
|
|
174
|
+
return Header_Get(this.Header, 'User-Agent')
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
public FormValue(key: string): string {
|
|
178
|
+
const query = this.URL?.Query
|
|
179
|
+
return typeof query === 'function' ? query.call(this.URL).Get(key) : ''
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
export class Response {
|
|
184
|
+
public StatusCode: number
|
|
185
|
+
public Body: io.ReadCloser | null
|
|
186
|
+
public Header: Header
|
|
187
|
+
|
|
188
|
+
constructor(init?: Partial<Response>) {
|
|
189
|
+
this.StatusCode = init?.StatusCode ?? 0
|
|
190
|
+
this.Body = init?.Body ?? null
|
|
191
|
+
this.Header = init?.Header ?? new Header()
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
public clone(): Response {
|
|
195
|
+
return new Response({
|
|
196
|
+
Body: this.Body,
|
|
197
|
+
Header: this.Header,
|
|
198
|
+
StatusCode: this.StatusCode,
|
|
199
|
+
})
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
export class Client {
|
|
204
|
+
public Transport: RoundTripper | null
|
|
205
|
+
|
|
206
|
+
constructor(init?: Partial<Client>) {
|
|
207
|
+
this.Transport = init?.Transport ?? null
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
public async Do(
|
|
211
|
+
_req: Request | $.VarRef<Request> | null,
|
|
212
|
+
): Promise<[Response | null, $.GoError]> {
|
|
213
|
+
return await (this.Transport ?? DefaultTransport).RoundTrip(_req)
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
export const DefaultClient = new Client()
|
|
218
|
+
|
|
219
|
+
export interface RoundTripper {
|
|
220
|
+
RoundTrip(req: Request | $.VarRef<Request> | null): [Response | null, $.GoError] | Promise<[Response | null, $.GoError]>
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
class unsupportedTransport implements RoundTripper {
|
|
224
|
+
public async RoundTrip(_req: Request | $.VarRef<Request> | null): Promise<[Response | null, $.GoError]> {
|
|
225
|
+
return [null, errors.New('net/http: Client.Do is not implemented in GoScript')]
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
export const DefaultTransport: RoundTripper = new unsupportedTransport()
|
|
230
|
+
|
|
231
|
+
export interface FileSystem {
|
|
232
|
+
Open(name: string): [File | null, $.GoError]
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
export interface File extends io.Closer, io.Reader, io.Seeker {
|
|
236
|
+
Readdir(count: number): [$.Slice<fs.FileInfo>, $.GoError]
|
|
237
|
+
Stat(): [fs.FileInfo, $.GoError]
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
export interface Handler {
|
|
241
|
+
ServeHTTP(w: ResponseWriter | null, r: Request | $.VarRef<Request> | null): void | Promise<void>
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
export type HandlerFunc = (
|
|
245
|
+
w: ResponseWriter | null,
|
|
246
|
+
r: Request | $.VarRef<Request> | null,
|
|
247
|
+
) => void | Promise<void>
|
|
248
|
+
|
|
249
|
+
export function HandlerFunc_ServeHTTP(
|
|
250
|
+
h: HandlerFunc,
|
|
251
|
+
w: ResponseWriter | null,
|
|
252
|
+
r: Request | $.VarRef<Request> | null,
|
|
253
|
+
): void | Promise<void> {
|
|
254
|
+
return h(w, r)
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
export class Server {
|
|
258
|
+
public Addr: string
|
|
259
|
+
public BaseContext: ((listener: any) => context.Context) | null
|
|
260
|
+
public Handler: Handler | null
|
|
261
|
+
public ReadHeaderTimeout: number
|
|
262
|
+
public WriteTimeout: number
|
|
263
|
+
|
|
264
|
+
constructor(init?: Partial<Server>) {
|
|
265
|
+
this.Addr = init?.Addr ?? ''
|
|
266
|
+
this.BaseContext = init?.BaseContext ?? null
|
|
267
|
+
this.Handler = init?.Handler ?? null
|
|
268
|
+
this.ReadHeaderTimeout = init?.ReadHeaderTimeout ?? 0
|
|
269
|
+
this.WriteTimeout = init?.WriteTimeout ?? 0
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
public ListenAndServe(): $.GoError {
|
|
273
|
+
return errors.New('net/http: Server.ListenAndServe is not implemented in GoScript')
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
public ListenAndServeTLS(_certFile: string, _keyFile: string): $.GoError {
|
|
277
|
+
return errors.New('net/http: Server.ListenAndServeTLS is not implemented in GoScript')
|
|
278
|
+
}
|
|
279
|
+
|
|
280
|
+
public Close(): $.GoError {
|
|
281
|
+
return null
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
public Shutdown(_ctx: context.Context): $.GoError {
|
|
285
|
+
return null
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
export class PushOptions {
|
|
290
|
+
public Header: Header
|
|
291
|
+
|
|
292
|
+
constructor(init?: Partial<PushOptions>) {
|
|
293
|
+
this.Header = init?.Header ?? new Header()
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
export interface Flusher {
|
|
298
|
+
Flush(): void
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
export interface Hijacker {
|
|
302
|
+
Hijack(): [any, any, $.GoError]
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
export interface Pusher {
|
|
306
|
+
Push(target: string, opts: PushOptions | $.VarRef<PushOptions> | null): $.GoError
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
export class ResponseController {
|
|
310
|
+
public rw: ResponseWriter | null
|
|
311
|
+
|
|
312
|
+
constructor(rw: ResponseWriter | null) {
|
|
313
|
+
this.rw = rw
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
public Flush(): $.GoError {
|
|
317
|
+
const flusher = this.rw as (Flusher & ResponseWriter) | null
|
|
318
|
+
flusher?.Flush?.()
|
|
319
|
+
return null
|
|
320
|
+
}
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
export function NewResponseController(rw: ResponseWriter | null): ResponseController {
|
|
324
|
+
return new ResponseController(rw)
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
export class ServeMux implements Handler {
|
|
328
|
+
private handlers = new Map<string, Handler>()
|
|
329
|
+
|
|
330
|
+
public Handle(pattern: string, handler: Handler | null): void {
|
|
331
|
+
if (handler != null) {
|
|
332
|
+
this.handlers.set(pattern, handler)
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
public HandleFunc(pattern: string, handler: HandlerFunc): void {
|
|
337
|
+
this.Handle(pattern, { ServeHTTP: handler })
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
public Handler(r: Request | $.VarRef<Request> | null): [Handler | null, string] {
|
|
341
|
+
const req = $.pointerValue<Request | null>(r)
|
|
342
|
+
const path = req?.URL?.Path ?? ''
|
|
343
|
+
const handler = this.handlers.get(path) ?? null
|
|
344
|
+
return [handler, handler == null ? '' : path]
|
|
345
|
+
}
|
|
346
|
+
|
|
347
|
+
public ServeHTTP(w: ResponseWriter | null, r: Request | $.VarRef<Request> | null): void | Promise<void> {
|
|
348
|
+
const [handler] = this.Handler(r)
|
|
349
|
+
if (handler == null) {
|
|
350
|
+
NotFound(w, r)
|
|
351
|
+
return
|
|
352
|
+
}
|
|
353
|
+
return handler.ServeHTTP(w, r)
|
|
354
|
+
}
|
|
355
|
+
}
|
|
356
|
+
|
|
357
|
+
const defaultServeMux = new ServeMux()
|
|
358
|
+
|
|
359
|
+
export function NewServeMux(): ServeMux {
|
|
360
|
+
return new ServeMux()
|
|
361
|
+
}
|
|
362
|
+
|
|
363
|
+
export function HandleFunc(pattern: string, handler: HandlerFunc): void {
|
|
364
|
+
defaultServeMux.HandleFunc(pattern, handler)
|
|
365
|
+
}
|
|
366
|
+
|
|
367
|
+
export function StripPrefix(prefix: string, handler: Handler | null): Handler {
|
|
368
|
+
return {
|
|
369
|
+
ServeHTTP(w, r) {
|
|
370
|
+
const req = $.pointerValue<Request | null>(r)
|
|
371
|
+
if (req?.URL != null && typeof req.URL.Path === 'string' && req.URL.Path.startsWith(prefix)) {
|
|
372
|
+
req.URL = { ...req.URL, Path: req.URL.Path.slice(prefix.length) || '/' }
|
|
373
|
+
}
|
|
374
|
+
return handler?.ServeHTTP(w, req)
|
|
375
|
+
},
|
|
376
|
+
}
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
export function Error(w: ResponseWriter | null, error: string, code: number): void {
|
|
380
|
+
w?.WriteHeader(code)
|
|
381
|
+
w?.Write($.stringToBytes(error + '\n'))
|
|
382
|
+
}
|
|
383
|
+
|
|
384
|
+
export function NotFound(w: ResponseWriter | null, _r: Request | $.VarRef<Request> | null): void {
|
|
385
|
+
Error(w, '404 page not found', StatusNotFound)
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
export function Redirect(
|
|
389
|
+
w: ResponseWriter | null,
|
|
390
|
+
_r: Request | $.VarRef<Request> | null,
|
|
391
|
+
url: string,
|
|
392
|
+
code: number,
|
|
393
|
+
): void {
|
|
394
|
+
const header = w?.Header()
|
|
395
|
+
if (header != null) {
|
|
396
|
+
Header_Set(header, 'Location', url)
|
|
397
|
+
}
|
|
398
|
+
w?.WriteHeader(code)
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
export function ParseTime(text: string): [time.Time, $.GoError] {
|
|
402
|
+
const date = new globalThis.Date(text)
|
|
403
|
+
if (isNaN(date.getTime())) {
|
|
404
|
+
return [new time.Time(), $.newError(`parsing time "${text}" as HTTP-date: cannot parse`)]
|
|
405
|
+
}
|
|
406
|
+
return [time.UnixMilli(date.getTime()), null]
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
export function NewRequest(
|
|
410
|
+
method: string,
|
|
411
|
+
url: string,
|
|
412
|
+
body: io.Reader | null,
|
|
413
|
+
): [Request | null, $.GoError] {
|
|
414
|
+
return NewRequestWithContext(null, method, url, body)
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
export function NewRequestWithContext(
|
|
418
|
+
_ctx: context.Context,
|
|
419
|
+
method: string,
|
|
420
|
+
url: string,
|
|
421
|
+
body: io.Reader | null,
|
|
422
|
+
): [Request | null, $.GoError] {
|
|
423
|
+
if (method === '') {
|
|
424
|
+
method = MethodGet
|
|
425
|
+
}
|
|
426
|
+
const parsedURL = parseRequestURL(url)
|
|
427
|
+
return [new Request({ Method: method, URL: parsedURL, Body: body, RequestURI: parsedURL.Path, ctx: _ctx }), null]
|
|
428
|
+
}
|
|
429
|
+
|
|
430
|
+
export function Get(_url: string): [Response | null, $.GoError] {
|
|
431
|
+
return [null, errors.New('net/http: Get is not implemented in GoScript')]
|
|
432
|
+
}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest'
|
|
2
|
+
|
|
3
|
+
import { Header, Header_Get, ResponseWriter } from '../index.js'
|
|
4
|
+
import { Handler, Index } from './index.js'
|
|
5
|
+
|
|
6
|
+
class writer implements ResponseWriter {
|
|
7
|
+
public status = 200
|
|
8
|
+
public header = new Header()
|
|
9
|
+
public chunks: number[] = []
|
|
10
|
+
|
|
11
|
+
Header(): Header {
|
|
12
|
+
return this.header
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
Write(p: number[] | null): [number, null] {
|
|
16
|
+
this.chunks.push(...(p ?? []))
|
|
17
|
+
return [p?.length ?? 0, null]
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
WriteHeader(statusCode: number): void {
|
|
21
|
+
this.status = statusCode
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
String(): string {
|
|
25
|
+
return Buffer.from(this.chunks).toString('utf8')
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
describe('net/http/pprof override', () => {
|
|
30
|
+
it('serves the index text expected by debug handlers', () => {
|
|
31
|
+
const w = new writer()
|
|
32
|
+
|
|
33
|
+
Index(w, null)
|
|
34
|
+
|
|
35
|
+
expect(Header_Get(w.Header(), 'Content-Type')).toContain('text/html')
|
|
36
|
+
expect(w.String()).toContain('full goroutine stack dump')
|
|
37
|
+
})
|
|
38
|
+
|
|
39
|
+
it('serves named runtime profiles', () => {
|
|
40
|
+
const w = new writer()
|
|
41
|
+
|
|
42
|
+
Handler('goroutine').ServeHTTP(w, null)
|
|
43
|
+
|
|
44
|
+
expect(Header_Get(w.Header(), 'Content-Type')).toContain('text/plain')
|
|
45
|
+
expect(w.String()).toContain('goroutine profile')
|
|
46
|
+
})
|
|
47
|
+
})
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import * as $ from '@goscript/builtin/index.js'
|
|
2
|
+
import * as http from '@goscript/net/http/index.js'
|
|
3
|
+
import * as pprof from '@goscript/runtime/pprof/index.js'
|
|
4
|
+
|
|
5
|
+
function writeString(w: http.ResponseWriter | null, value: string): void {
|
|
6
|
+
w?.Write($.stringToBytes(value))
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export function Index(w: http.ResponseWriter | null, _r: http.Request | $.VarRef<http.Request> | null): void {
|
|
10
|
+
const header = w?.Header()
|
|
11
|
+
if (header != null) {
|
|
12
|
+
http.Header_Set(header, 'Content-Type', 'text/html; charset=utf-8')
|
|
13
|
+
}
|
|
14
|
+
writeString(w, '<html><body><a href="goroutine?debug=2">full goroutine stack dump</a></body></html>')
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export function Cmdline(w: http.ResponseWriter | null, _r: http.Request | $.VarRef<http.Request> | null): void {
|
|
18
|
+
const header = w?.Header()
|
|
19
|
+
if (header != null) {
|
|
20
|
+
http.Header_Set(header, 'Content-Type', 'text/plain; charset=utf-8')
|
|
21
|
+
}
|
|
22
|
+
writeString(w, 'goscript')
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export function Profile(w: http.ResponseWriter | null, _r: http.Request | $.VarRef<http.Request> | null): void {
|
|
26
|
+
const header = w?.Header()
|
|
27
|
+
if (header != null) {
|
|
28
|
+
http.Header_Set(header, 'Content-Type', 'application/octet-stream')
|
|
29
|
+
}
|
|
30
|
+
writeString(w, 'cpu profile\n')
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export function Symbol(w: http.ResponseWriter | null, _r: http.Request | $.VarRef<http.Request> | null): void {
|
|
34
|
+
const header = w?.Header()
|
|
35
|
+
if (header != null) {
|
|
36
|
+
http.Header_Set(header, 'Content-Type', 'text/plain; charset=utf-8')
|
|
37
|
+
}
|
|
38
|
+
writeString(w, 'num_symbols: 0\n')
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export function Trace(w: http.ResponseWriter | null, _r: http.Request | $.VarRef<http.Request> | null): void {
|
|
42
|
+
const header = w?.Header()
|
|
43
|
+
if (header != null) {
|
|
44
|
+
http.Header_Set(header, 'Content-Type', 'application/octet-stream')
|
|
45
|
+
}
|
|
46
|
+
writeString(w, 'trace\n')
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
export function Handler(name: string): http.Handler {
|
|
50
|
+
return {
|
|
51
|
+
ServeHTTP(w) {
|
|
52
|
+
const header = w?.Header()
|
|
53
|
+
if (header != null) {
|
|
54
|
+
http.Header_Set(header, 'Content-Type', 'text/plain; charset=utf-8')
|
|
55
|
+
}
|
|
56
|
+
const profile = pprof.Lookup(name)
|
|
57
|
+
if (profile == null) {
|
|
58
|
+
http.NotFound(w, null)
|
|
59
|
+
return
|
|
60
|
+
}
|
|
61
|
+
writeString(w, `${name} profile\n`)
|
|
62
|
+
profile.WriteTo(w, 1)
|
|
63
|
+
},
|
|
64
|
+
}
|
|
65
|
+
}
|