@bytecodealliance/preview2-shim 0.0.19 → 0.0.21
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/LICENSE +220 -0
- package/README.md +4 -6
- package/lib/browser/cli.js +79 -12
- package/lib/browser/filesystem.js +168 -198
- package/lib/browser/index.js +1 -5
- package/lib/browser/io.js +173 -29
- package/lib/common/io.js +6 -4
- package/lib/{http → common}/make-request.js +1 -1
- package/lib/nodejs/cli.js +5 -4
- package/lib/nodejs/filesystem.js +106 -73
- package/lib/nodejs/http.js +309 -3
- package/lib/nodejs/index.js +0 -5
- package/package.json +1 -1
- package/types/interfaces/wasi-cli-stderr.d.ts +1 -1
- package/types/interfaces/wasi-cli-stdin.d.ts +1 -1
- package/types/interfaces/wasi-cli-stdout.d.ts +1 -1
- package/types/interfaces/wasi-cli-terminal-stderr.d.ts +1 -1
- package/types/interfaces/wasi-cli-terminal-stdin.d.ts +1 -1
- package/types/interfaces/wasi-cli-terminal-stdout.d.ts +1 -1
- package/types/interfaces/wasi-clocks-monotonic-clock.d.ts +1 -1
- package/types/interfaces/wasi-clocks-timezone.d.ts +1 -1
- package/types/interfaces/wasi-filesystem-preopens.d.ts +1 -1
- package/types/interfaces/wasi-filesystem-types.d.ts +8 -8
- package/types/interfaces/wasi-http-incoming-handler.d.ts +19 -0
- package/types/interfaces/wasi-http-outgoing-handler.d.ts +23 -0
- package/types/interfaces/wasi-http-types.d.ts +371 -0
- package/types/interfaces/wasi-io-streams.d.ts +13 -21
- package/types/interfaces/wasi-sockets-instance-network.d.ts +1 -1
- package/types/interfaces/wasi-sockets-ip-name-lookup.d.ts +5 -5
- package/types/interfaces/wasi-sockets-tcp-create-socket.d.ts +4 -4
- package/types/interfaces/wasi-sockets-tcp.d.ts +7 -7
- package/types/interfaces/wasi-sockets-udp-create-socket.d.ts +4 -4
- package/types/interfaces/wasi-sockets-udp.d.ts +5 -5
- package/types/wasi-cli-command.d.ts +3 -3
- package/types/wasi-http-proxy.d.ts +13 -0
- package/lib/browser/poll.js +0 -53
- package/lib/http/wasi-http.js +0 -382
- package/lib/nodejs/poll.js +0 -9
- /package/lib/{http/synckit → synckit}/index.d.ts +0 -0
- /package/lib/{http/synckit → synckit}/index.js +0 -0
package/lib/nodejs/http.js
CHANGED
|
@@ -1,5 +1,311 @@
|
|
|
1
|
-
import { WasiHttp } from '../http/wasi-http.js';
|
|
2
1
|
import { streams } from '../common/io.js';
|
|
2
|
+
import { fileURLToPath } from 'node:url';
|
|
3
|
+
import { createSyncFn } from '../synckit/index.js';
|
|
3
4
|
|
|
4
|
-
const
|
|
5
|
-
|
|
5
|
+
const { InputStream, OutputStream } = streams;
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* @typedef {import("../../types/interfaces/wasi-http-types").Method} Method
|
|
9
|
+
* @typedef {import("../../types/interfaces/wasi-http-types").RequestOptions} RequestOptions
|
|
10
|
+
* @typedef {import("../../types/interfaces/wasi-http-types").Scheme} Scheme
|
|
11
|
+
* @typedef {import("../../types/interfaces/wasi-http-types").Error} HttpError
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
const workerPath = fileURLToPath(new URL('../common/make-request.js', import.meta.url));
|
|
15
|
+
|
|
16
|
+
function send(req) {
|
|
17
|
+
const syncFn = createSyncFn(workerPath);
|
|
18
|
+
let rawResponse = syncFn(req);
|
|
19
|
+
let response = JSON.parse(rawResponse);
|
|
20
|
+
if (response.status) {
|
|
21
|
+
return {
|
|
22
|
+
...response,
|
|
23
|
+
body: response.body ? Buffer.from(response.body, 'base64') : undefined,
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
// HttpError
|
|
27
|
+
throw { tag: 'unexpected-error', val: response.message };
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
function combineChunks (chunks) {
|
|
31
|
+
if (chunks.length === 0)
|
|
32
|
+
return new Uint8Array();
|
|
33
|
+
if (chunks.length === 1)
|
|
34
|
+
return chunks[0];
|
|
35
|
+
const totalLen = chunks.reduce((total, chunk) => total + chunk.byteLength);
|
|
36
|
+
const out = new Uint8Array(totalLen);
|
|
37
|
+
let idx = 0;
|
|
38
|
+
for (const chunk of chunks) {
|
|
39
|
+
out.set(chunk, idx);
|
|
40
|
+
idx += chunk.byteLength;
|
|
41
|
+
}
|
|
42
|
+
return out;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export class WasiHttp {
|
|
46
|
+
requestCnt = 1;
|
|
47
|
+
responseCnt = 1;
|
|
48
|
+
fieldsCnt = 1;
|
|
49
|
+
futureCnt = 1;
|
|
50
|
+
|
|
51
|
+
constructor() {
|
|
52
|
+
const http = this;
|
|
53
|
+
|
|
54
|
+
class IncomingBody {
|
|
55
|
+
#bodyFinished = false;
|
|
56
|
+
#chunks = [];
|
|
57
|
+
stream () {
|
|
58
|
+
const incomingBody = this;
|
|
59
|
+
return new InputStream({
|
|
60
|
+
blockingRead (_len) {
|
|
61
|
+
if (incomingBody.#bodyFinished)
|
|
62
|
+
throw { tag: 'closed' };
|
|
63
|
+
if (incomingBody.#chunks.length === 0)
|
|
64
|
+
return new Uint8Array([]);
|
|
65
|
+
// TODO: handle chunk splitting case where len is less than chunk length
|
|
66
|
+
return incomingBody.#chunks.shift();
|
|
67
|
+
},
|
|
68
|
+
subscribe () {
|
|
69
|
+
// TODO
|
|
70
|
+
}
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
static finish (incomingBody) {
|
|
74
|
+
incomingBody.#bodyFinished = true;
|
|
75
|
+
return futureTrailersCreate(new Fields([]), false);
|
|
76
|
+
}
|
|
77
|
+
static _addChunk (incomingBody, chunk) {
|
|
78
|
+
incomingBody.#chunks.push(chunk);
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
const incomingBodyAddChunk = IncomingBody._addChunk;
|
|
82
|
+
delete IncomingBody._addChunk;
|
|
83
|
+
|
|
84
|
+
// TODO
|
|
85
|
+
class IncomingRequest {}
|
|
86
|
+
|
|
87
|
+
class FutureTrailers {
|
|
88
|
+
id = this.futureCnt++;
|
|
89
|
+
#value;
|
|
90
|
+
#isError;
|
|
91
|
+
subscribe () {
|
|
92
|
+
// TODO
|
|
93
|
+
}
|
|
94
|
+
get () {
|
|
95
|
+
return { tag: this.#isError ? 'err' : 'ok', val: this.#value };
|
|
96
|
+
}
|
|
97
|
+
static _create (value, isError) {
|
|
98
|
+
const res = new FutureTrailers();
|
|
99
|
+
res.#value = value;
|
|
100
|
+
res.#isError = isError;
|
|
101
|
+
return res;
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
const futureTrailersCreate = FutureTrailers._create;
|
|
105
|
+
delete FutureTrailers._create;
|
|
106
|
+
|
|
107
|
+
class OutgoingResponse {
|
|
108
|
+
id = http.responseCnt++;
|
|
109
|
+
/** @type {number} */ _statusCode;
|
|
110
|
+
/** @type {Fields} */ _headers;
|
|
111
|
+
|
|
112
|
+
/**
|
|
113
|
+
* @param {number} statusCode
|
|
114
|
+
* @param {Fields} headers
|
|
115
|
+
*/
|
|
116
|
+
constructor (statusCode, headers) {
|
|
117
|
+
this._statusCode = statusCode;
|
|
118
|
+
this.headers = headers;
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
class ResponseOutparam {
|
|
123
|
+
static set (_param, _response) {
|
|
124
|
+
// TODO
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
class OutgoingRequest {
|
|
129
|
+
id = http.requestCnt++;
|
|
130
|
+
/** @type {Method} */ #method = { tag: 'get' };
|
|
131
|
+
/** @type {Scheme | undefined} */ #scheme = { tag: 'HTTP' };
|
|
132
|
+
/** @type {string | undefined} */ #pathWithQuery = undefined;
|
|
133
|
+
/** @type {string | undefined} */ #authority = undefined;
|
|
134
|
+
/** @type {Fields} */ #headers = undefined;
|
|
135
|
+
/** @type {OutgoingBody} */ #body = new OutgoingBody();
|
|
136
|
+
constructor(method, pathWithQuery, scheme, authority, headers) {
|
|
137
|
+
this.#method = method;
|
|
138
|
+
this.#pathWithQuery = pathWithQuery;
|
|
139
|
+
this.#scheme = scheme;
|
|
140
|
+
this.#authority = authority;
|
|
141
|
+
this.#headers = headers;
|
|
142
|
+
}
|
|
143
|
+
write () {
|
|
144
|
+
return this.#body;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
static _handle (request) {
|
|
148
|
+
const scheme = request.#scheme.tag === "HTTP" ? "http://" : "https://";
|
|
149
|
+
const url = scheme + request.#authority + request.#pathWithQuery;
|
|
150
|
+
const headers = {
|
|
151
|
+
"host": request.#authority,
|
|
152
|
+
};
|
|
153
|
+
const decoder = new TextDecoder();
|
|
154
|
+
for (const [key, value] of request.#headers.entries()) {
|
|
155
|
+
headers[key] = decoder.decode(value);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
let res;
|
|
159
|
+
try {
|
|
160
|
+
res = send({
|
|
161
|
+
method: request.#method.tag,
|
|
162
|
+
uri: url,
|
|
163
|
+
headers: headers,
|
|
164
|
+
params: [],
|
|
165
|
+
body: combineChunks(outgoingBodyGetChunks(request.#body)),
|
|
166
|
+
});
|
|
167
|
+
} catch (err) {
|
|
168
|
+
return newFutureIncomingResponse(err.toString(), true);
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const encoder = new TextEncoder();
|
|
172
|
+
const response = newIncomingResponse(res.status, new Fields(res.headers.map(([key, value]) => [key, encoder.encode(value)])), [res.body]);
|
|
173
|
+
return newFutureIncomingResponse({ tag: 'ok', val: response }, false);
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
const outgoingRequestHandle = OutgoingRequest._handle;
|
|
178
|
+
delete OutgoingRequest._handle;
|
|
179
|
+
|
|
180
|
+
class OutgoingBody {
|
|
181
|
+
#chunks = [];
|
|
182
|
+
write () {
|
|
183
|
+
const body = this;
|
|
184
|
+
return new OutputStream({
|
|
185
|
+
write (bytes) {
|
|
186
|
+
body.#chunks.push(bytes);
|
|
187
|
+
},
|
|
188
|
+
blockingFlush () {}
|
|
189
|
+
});
|
|
190
|
+
}
|
|
191
|
+
/**
|
|
192
|
+
* @param {OutgoingBody} body
|
|
193
|
+
* @param {Fields | undefined} trailers
|
|
194
|
+
*/
|
|
195
|
+
static finish (_body, _trailers) {
|
|
196
|
+
// TODO
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
static _getChunks (body) {
|
|
200
|
+
return body.#chunks;
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
const outgoingBodyGetChunks = OutgoingBody._getChunks;
|
|
204
|
+
delete OutgoingBody._getChunks;
|
|
205
|
+
|
|
206
|
+
class IncomingResponse {
|
|
207
|
+
id = http.responseCnt++;
|
|
208
|
+
/** @type {InputStream} */ #body;
|
|
209
|
+
/** @type {Fields} */ #headers = undefined;
|
|
210
|
+
#status = 0;
|
|
211
|
+
#bodyConsumed = false;
|
|
212
|
+
status () {
|
|
213
|
+
return this.#status;
|
|
214
|
+
}
|
|
215
|
+
headers () {
|
|
216
|
+
return this.#headers;
|
|
217
|
+
}
|
|
218
|
+
consume () {
|
|
219
|
+
if (this.#bodyConsumed)
|
|
220
|
+
throw { tag: 'unexpected-error', val: 'request body already consumed' };
|
|
221
|
+
this.#bodyConsumed = true;
|
|
222
|
+
return this.#body;
|
|
223
|
+
}
|
|
224
|
+
static _create (status, headers, chunks) {
|
|
225
|
+
const res = new IncomingResponse();
|
|
226
|
+
res.#status = status;
|
|
227
|
+
res.#headers = headers;
|
|
228
|
+
res.#body = new IncomingBody();
|
|
229
|
+
for (const chunk of chunks) {
|
|
230
|
+
incomingBodyAddChunk(res.#body, chunk);
|
|
231
|
+
}
|
|
232
|
+
return res;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
const newIncomingResponse = IncomingResponse._create;
|
|
237
|
+
delete IncomingResponse._create;
|
|
238
|
+
|
|
239
|
+
class FutureIncomingResponse {
|
|
240
|
+
id = this.futureCnt++;
|
|
241
|
+
#value;
|
|
242
|
+
#isError;
|
|
243
|
+
subscribe () {
|
|
244
|
+
// TODO
|
|
245
|
+
}
|
|
246
|
+
get () {
|
|
247
|
+
return { tag: this.#isError ? 'err' : 'ok', val: this.#value };
|
|
248
|
+
}
|
|
249
|
+
static _create (value, isError) {
|
|
250
|
+
const res = new FutureIncomingResponse();
|
|
251
|
+
res.#value = value;
|
|
252
|
+
res.#isError = isError;
|
|
253
|
+
return res;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
const newFutureIncomingResponse = FutureIncomingResponse._create;
|
|
258
|
+
delete FutureIncomingResponse._create;
|
|
259
|
+
|
|
260
|
+
class Fields {
|
|
261
|
+
id = http.fieldsCnt++;
|
|
262
|
+
/** @type {Record<string, Uint8Array[]>} */ #fields;
|
|
263
|
+
|
|
264
|
+
/**
|
|
265
|
+
* @param {[string, Uint8Array[]][]} fields
|
|
266
|
+
*/
|
|
267
|
+
constructor(fields) {
|
|
268
|
+
this.#fields = Object.fromEntries(fields);
|
|
269
|
+
}
|
|
270
|
+
get (name) {
|
|
271
|
+
return this.#fields[name];
|
|
272
|
+
}
|
|
273
|
+
set (name, value) {
|
|
274
|
+
this.#fields[name] = value;
|
|
275
|
+
}
|
|
276
|
+
delete (name) {
|
|
277
|
+
delete this.#fields[name];
|
|
278
|
+
}
|
|
279
|
+
entries () {
|
|
280
|
+
return Object.entries(this.#fields);
|
|
281
|
+
}
|
|
282
|
+
clone () {
|
|
283
|
+
return new Fields(this.entries());
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
this.outgoingHandler = {
|
|
288
|
+
/**
|
|
289
|
+
* @param {OutgoingRequest} request
|
|
290
|
+
* @param {RequestOptions | undefined} _options
|
|
291
|
+
* @returns {FutureIncomingResponse}
|
|
292
|
+
*/
|
|
293
|
+
handle: outgoingRequestHandle
|
|
294
|
+
};
|
|
295
|
+
|
|
296
|
+
this.types = {
|
|
297
|
+
Fields,
|
|
298
|
+
FutureIncomingResponse,
|
|
299
|
+
FutureTrailers,
|
|
300
|
+
IncomingBody,
|
|
301
|
+
IncomingRequest,
|
|
302
|
+
IncomingResponse,
|
|
303
|
+
OutgoingBody,
|
|
304
|
+
OutgoingRequest,
|
|
305
|
+
OutgoingResponse,
|
|
306
|
+
ResponseOutparam
|
|
307
|
+
};
|
|
308
|
+
}
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
export const { outgoingHandler, types } = new WasiHttp();
|
package/lib/nodejs/index.js
CHANGED
|
@@ -2,7 +2,6 @@ import * as clocks from "./clocks.js";
|
|
|
2
2
|
import * as filesystem from "./filesystem.js";
|
|
3
3
|
import * as http from "./http.js";
|
|
4
4
|
import * as io from "../common/io.js";
|
|
5
|
-
import * as poll from "./poll.js";
|
|
6
5
|
import * as random from "./random.js";
|
|
7
6
|
import * as sockets from "./sockets.js";
|
|
8
7
|
import * as cli from "./cli.js";
|
|
@@ -12,11 +11,7 @@ export {
|
|
|
12
11
|
filesystem,
|
|
13
12
|
http,
|
|
14
13
|
io,
|
|
15
|
-
poll,
|
|
16
14
|
random,
|
|
17
15
|
sockets,
|
|
18
16
|
cli
|
|
19
17
|
}
|
|
20
|
-
|
|
21
|
-
export { WasiHttp } from "../http/wasi-http.js";
|
|
22
|
-
|
package/package.json
CHANGED
|
@@ -5,5 +5,5 @@ export namespace WasiCliTerminalStderr {
|
|
|
5
5
|
*/
|
|
6
6
|
export function getTerminalStderr(): TerminalOutput | undefined;
|
|
7
7
|
}
|
|
8
|
-
import type { TerminalOutput } from '../interfaces/wasi-cli-terminal-output';
|
|
8
|
+
import type { TerminalOutput } from '../interfaces/wasi-cli-terminal-output.js';
|
|
9
9
|
export { TerminalOutput };
|
|
@@ -5,5 +5,5 @@ export namespace WasiCliTerminalStdin {
|
|
|
5
5
|
*/
|
|
6
6
|
export function getTerminalStdin(): TerminalInput | undefined;
|
|
7
7
|
}
|
|
8
|
-
import type { TerminalInput } from '../interfaces/wasi-cli-terminal-input';
|
|
8
|
+
import type { TerminalInput } from '../interfaces/wasi-cli-terminal-input.js';
|
|
9
9
|
export { TerminalInput };
|
|
@@ -5,5 +5,5 @@ export namespace WasiCliTerminalStdout {
|
|
|
5
5
|
*/
|
|
6
6
|
export function getTerminalStdout(): TerminalOutput | undefined;
|
|
7
7
|
}
|
|
8
|
-
import type { TerminalOutput } from '../interfaces/wasi-cli-terminal-output';
|
|
8
|
+
import type { TerminalOutput } from '../interfaces/wasi-cli-terminal-output.js';
|
|
9
9
|
export { TerminalOutput };
|
|
@@ -16,7 +16,7 @@ export namespace WasiClocksMonotonicClock {
|
|
|
16
16
|
*/
|
|
17
17
|
export function subscribe(when: Instant, absolute: boolean): Pollable;
|
|
18
18
|
}
|
|
19
|
-
import type { Pollable } from '../interfaces/wasi-io-poll';
|
|
19
|
+
import type { Pollable } from '../interfaces/wasi-io-poll.js';
|
|
20
20
|
export { Pollable };
|
|
21
21
|
/**
|
|
22
22
|
* A timestamp in nanoseconds.
|
|
@@ -14,7 +14,7 @@ export namespace WasiClocksTimezone {
|
|
|
14
14
|
*/
|
|
15
15
|
export function utcOffset(when: Datetime): number;
|
|
16
16
|
}
|
|
17
|
-
import type { Datetime } from '../interfaces/wasi-clocks-wall-clock';
|
|
17
|
+
import type { Datetime } from '../interfaces/wasi-clocks-wall-clock.js';
|
|
18
18
|
export { Datetime };
|
|
19
19
|
/**
|
|
20
20
|
* Information useful for displaying the timezone of a specific `datetime`.
|
|
@@ -4,5 +4,5 @@ export namespace WasiFilesystemPreopens {
|
|
|
4
4
|
*/
|
|
5
5
|
export function getDirectories(): [Descriptor, string][];
|
|
6
6
|
}
|
|
7
|
-
import type { Descriptor } from '../interfaces/wasi-filesystem-types';
|
|
7
|
+
import type { Descriptor } from '../interfaces/wasi-filesystem-types.js';
|
|
8
8
|
export { Descriptor };
|
|
@@ -391,13 +391,13 @@ export namespace WasiFilesystemTypes {
|
|
|
391
391
|
*/
|
|
392
392
|
export function filesystemErrorCode(err: Error): ErrorCode | undefined;
|
|
393
393
|
}
|
|
394
|
-
import type { InputStream } from '../interfaces/wasi-io-streams';
|
|
394
|
+
import type { InputStream } from '../interfaces/wasi-io-streams.js';
|
|
395
395
|
export { InputStream };
|
|
396
|
-
import type { OutputStream } from '../interfaces/wasi-io-streams';
|
|
396
|
+
import type { OutputStream } from '../interfaces/wasi-io-streams.js';
|
|
397
397
|
export { OutputStream };
|
|
398
|
-
import type { Error } from '../interfaces/wasi-io-streams';
|
|
398
|
+
import type { Error } from '../interfaces/wasi-io-streams.js';
|
|
399
399
|
export { Error };
|
|
400
|
-
import type { Datetime } from '../interfaces/wasi-clocks-wall-clock';
|
|
400
|
+
import type { Datetime } from '../interfaces/wasi-clocks-wall-clock.js';
|
|
401
401
|
export { Datetime };
|
|
402
402
|
/**
|
|
403
403
|
* File size or length of a region within a file.
|
|
@@ -808,10 +808,6 @@ export interface MetadataHashValue {
|
|
|
808
808
|
upper: bigint,
|
|
809
809
|
}
|
|
810
810
|
|
|
811
|
-
export class DirectoryEntryStream {
|
|
812
|
-
readDirectoryEntry(): DirectoryEntry | undefined;
|
|
813
|
-
}
|
|
814
|
-
|
|
815
811
|
export class Descriptor {
|
|
816
812
|
readViaStream(offset: Filesize): InputStream;
|
|
817
813
|
writeViaStream(offset: Filesize): OutputStream;
|
|
@@ -849,3 +845,7 @@ export class Descriptor {
|
|
|
849
845
|
metadataHash(): MetadataHashValue;
|
|
850
846
|
metadataHashAt(pathFlags: PathFlags, path: string): MetadataHashValue;
|
|
851
847
|
}
|
|
848
|
+
|
|
849
|
+
export class DirectoryEntryStream {
|
|
850
|
+
readDirectoryEntry(): DirectoryEntry | undefined;
|
|
851
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export namespace WasiHttpIncomingHandler {
|
|
2
|
+
/**
|
|
3
|
+
* This function is invoked with an incoming HTTP Request, and a resource
|
|
4
|
+
* `response-outparam` which provides the capability to reply with an HTTP
|
|
5
|
+
* Response. The response is sent by calling the `response-outparam.set`
|
|
6
|
+
* method, which allows execution to continue after the response has been
|
|
7
|
+
* sent. This enables both streaming to the response body, and performing other
|
|
8
|
+
* work.
|
|
9
|
+
*
|
|
10
|
+
* The implementor of this function must write a response to the
|
|
11
|
+
* `response-outparam` before returning, or else the caller will respond
|
|
12
|
+
* with an error on its behalf.
|
|
13
|
+
*/
|
|
14
|
+
export function handle(request: IncomingRequest, responseOut: ResponseOutparam): void;
|
|
15
|
+
}
|
|
16
|
+
import type { IncomingRequest } from '../interfaces/wasi-http-types.js';
|
|
17
|
+
export { IncomingRequest };
|
|
18
|
+
import type { ResponseOutparam } from '../interfaces/wasi-http-types.js';
|
|
19
|
+
export { ResponseOutparam };
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
export namespace WasiHttpOutgoingHandler {
|
|
2
|
+
/**
|
|
3
|
+
* This function is invoked with an outgoing HTTP Request, and it returns
|
|
4
|
+
* a resource `future-incoming-response` which represents an HTTP Response
|
|
5
|
+
* which may arrive in the future.
|
|
6
|
+
*
|
|
7
|
+
* The `options` argument accepts optional parameters for the HTTP
|
|
8
|
+
* protocol's transport layer.
|
|
9
|
+
*
|
|
10
|
+
* This function may return an error if the `outgoing-request` is invalid
|
|
11
|
+
* or not allowed to be made. Otherwise, protocol errors are reported
|
|
12
|
+
* through the `future-incoming-response`.
|
|
13
|
+
*/
|
|
14
|
+
export function handle(request: OutgoingRequest, options: RequestOptions | undefined): FutureIncomingResponse;
|
|
15
|
+
}
|
|
16
|
+
import type { OutgoingRequest } from '../interfaces/wasi-http-types.js';
|
|
17
|
+
export { OutgoingRequest };
|
|
18
|
+
import type { RequestOptions } from '../interfaces/wasi-http-types.js';
|
|
19
|
+
export { RequestOptions };
|
|
20
|
+
import type { FutureIncomingResponse } from '../interfaces/wasi-http-types.js';
|
|
21
|
+
export { FutureIncomingResponse };
|
|
22
|
+
import type { Error } from '../interfaces/wasi-http-types.js';
|
|
23
|
+
export { Error };
|