diff options
Diffstat (limited to 'src/bun.js')
-rw-r--r-- | src/bun.js/bindings/ZigGlobalObject.cpp | 2 | ||||
-rw-r--r-- | src/bun.js/bindings/bindings.cpp | 97 | ||||
-rw-r--r-- | src/bun.js/bindings/bindings.zig | 79 | ||||
-rw-r--r-- | src/bun.js/bindings/headers-cpp.h | 16 | ||||
-rw-r--r-- | src/bun.js/bindings/headers.h | 17 | ||||
-rw-r--r-- | src/bun.js/bindings/headers.zig | 9 | ||||
-rw-r--r-- | src/bun.js/bindings/sizes.zig | 2 | ||||
-rw-r--r-- | src/bun.js/bindings/webcore/AbortSignal.cpp | 6 | ||||
-rw-r--r-- | src/bun.js/bindings/webcore/AbortSignal.h | 2 | ||||
-rw-r--r-- | src/bun.js/event_loop.zig | 1 | ||||
-rw-r--r-- | src/bun.js/javascript.zig | 2 | ||||
-rw-r--r-- | src/bun.js/webcore/response.zig | 45 |
12 files changed, 264 insertions, 14 deletions
diff --git a/src/bun.js/bindings/ZigGlobalObject.cpp b/src/bun.js/bindings/ZigGlobalObject.cpp index 0f4fe92e2..8fd9f366a 100644 --- a/src/bun.js/bindings/ZigGlobalObject.cpp +++ b/src/bun.js/bindings/ZigGlobalObject.cpp @@ -1533,7 +1533,7 @@ JSC_DEFINE_HOST_FUNCTION(whenSignalAborted, (JSGlobalObject * globalObject, Call Ref<AbortAlgorithm> abortAlgorithm = JSAbortAlgorithm::create(vm, callFrame->uncheckedArgument(1).getObject()); - bool result = AbortSignal::whenSignalAborted(abortSignal->wrapped(), WTFMove(abortAlgorithm)); + bool result = WebCore::AbortSignal::whenSignalAborted(abortSignal->wrapped(), WTFMove(abortAlgorithm)); return JSValue::encode(result ? JSValue(JSC::JSValue::JSTrue) : JSValue(JSC::JSValue::JSFalse)); } diff --git a/src/bun.js/bindings/bindings.cpp b/src/bun.js/bindings/bindings.cpp index aa8a28601..4b614788d 100644 --- a/src/bun.js/bindings/bindings.cpp +++ b/src/bun.js/bindings/bindings.cpp @@ -84,6 +84,8 @@ #include "JavaScriptCore/PropertyNameArray.h" #include "JavaScriptCore/HashMapImpl.h" #include "JavaScriptCore/HashMapImplInlines.h" +#include "webcore/JSAbortSignal.h" +#include "JSAbortAlgorithm.h" #include "DOMFormData.h" #include "JSDOMFormData.h" @@ -3732,6 +3734,101 @@ extern "C" void JSC__JSGlobalObject__queueMicrotaskJob(JSC__JSGlobalObject* arg0 JSC::JSValue::decode(JSValue4)); } +extern "C" JSC__AbortSignal* JSC__AbortSignal__signal(JSC__AbortSignal* arg0, JSC__JSValue JSValue1) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + abortSignal->signalAbort(JSC::JSValue::decode(JSValue1)); + return arg0; +} + +extern "C" bool JSC__AbortSignal__aborted(JSC__AbortSignal* arg0) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + return abortSignal->aborted(); +} + +extern "C" JSC__JSValue JSC__AbortSignal__abortReason(JSC__AbortSignal* arg0) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + return JSC::JSValue::encode(abortSignal->reason().getValue()); +} + + +extern "C" JSC__AbortSignal* JSC__AbortSignal__ref(JSC__AbortSignal* arg0) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + abortSignal->ref(); + return arg0; +} + +extern "C" JSC__AbortSignal* JSC__AbortSignal__unref(JSC__AbortSignal* arg0) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + abortSignal->deref(); + return arg0; +} + +extern "C" JSC__AbortSignal* JSC__AbortSignal__addListener(JSC__AbortSignal* arg0, void* ctx, void (*callback)(void* ctx, JSC__JSValue reason)) { + WebCore::AbortSignal* abortSignal = reinterpret_cast<WebCore::AbortSignal*>(arg0); + + if(abortSignal->aborted()){ + callback(ctx, JSC::JSValue::encode(abortSignal->reason().getValue())); + return arg0; + } + + abortSignal->addNativeCallback(std::make_tuple(ctx, callback)); + + return arg0; +} +extern "C" JSC__AbortSignal* JSC__AbortSignal__fromJS(JSC__JSValue value) +{ + JSC::JSValue decodedValue = JSC::JSValue::decode(value); + if (decodedValue.isEmpty()) + return nullptr; + WebCore::JSAbortSignal* object = JSC::jsDynamicCast<WebCore::JSAbortSignal*>(decodedValue); + if (!object) + return nullptr; + + return reinterpret_cast<JSC__AbortSignal*>(&object->wrapped()); +} +static auto ABORT_ERROR_NAME = MAKE_STATIC_STRING_IMPL("AbortError"); +extern "C" JSC__JSValue JSC__AbortSignal__createAbortError(const ZigString* message, const ZigString* arg1, + JSC__JSGlobalObject* globalObject) +{ + JSC::VM& vm = globalObject->vm(); + ZigString code = *arg1; + JSC::JSObject* error = Zig::getErrorInstance(message, globalObject).asCell()->getObject(); + + error->putDirect( + vm, vm.propertyNames->name, + JSC::JSValue(JSC::jsOwnedString(vm, ABORT_ERROR_NAME)), + 0); + + if (code.len > 0) { + auto clientData = WebCore::clientData(vm); + JSC::JSValue codeValue = Zig::toJSStringValue(code, globalObject); + error->putDirect(vm, clientData->builtinNames().codePublicName(), codeValue, 0); + } + + return JSC::JSValue::encode(error); +} + +static auto TIMEOUT_ERROR_NAME = MAKE_STATIC_STRING_IMPL("TimeoutError"); +extern "C" JSC__JSValue JSC__AbortSignal__createTimeoutError(const ZigString* message, const ZigString* arg1, + JSC__JSGlobalObject* globalObject) +{ + JSC::VM& vm = globalObject->vm(); + ZigString code = *arg1; + JSC::JSObject* error = Zig::getErrorInstance(message, globalObject).asCell()->getObject(); + + error->putDirect( + vm, vm.propertyNames->name, + JSC::JSValue(JSC::jsOwnedString(vm, TIMEOUT_ERROR_NAME)), + 0); + + if (code.len > 0) { + auto clientData = WebCore::clientData(vm); + JSC::JSValue codeValue = Zig::toJSStringValue(code, globalObject); + error->putDirect(vm, clientData->builtinNames().codePublicName(), codeValue, 0); + } + + return JSC::JSValue::encode(error); +} #pragma mark - WebCore::DOMFormData CPP_DECL void WebCore__DOMFormData__append(WebCore__DOMFormData* arg0, ZigString* arg1, ZigString* arg2) diff --git a/src/bun.js/bindings/bindings.zig b/src/bun.js/bindings/bindings.zig index 4c1469564..6b5386a68 100644 --- a/src/bun.js/bindings/bindings.zig +++ b/src/bun.js/bindings/bindings.zig @@ -209,12 +209,19 @@ pub const ZigString = extern struct { return ZigString__toJSONObject(&this, globalThis); } - pub fn substring(this: ZigString, offset: usize) ZigString { + pub fn substring(this: ZigString, offset: usize, maxlen: usize) ZigString { + var len: usize = undefined; + if(maxlen == 0){ + len = this.len; + }else { + len = @max(this.len, maxlen); + } + if (this.is16Bit()) { - return ZigString.from16Slice(this.utf16SliceAligned()[@min(this.len, offset)..]); + return ZigString.from16Slice(this.utf16SliceAligned()[@min(this.len, offset)..len]); } - var out = ZigString.init(this.slice()[@min(this.len, offset)..]); + var out = ZigString.init(this.slice()[@min(this.len, offset)..len]); if (this.isUTF8()) { out.markUTF8(); } @@ -1662,6 +1669,72 @@ pub fn PromiseCallback(comptime Type: type, comptime CallbackFunction: fn (*Type }.callback; } +pub const AbortSignal = extern opaque { + pub const shim = Shimmer("JSC", "AbortSignal", @This()); + const cppFn = shim.cppFn; + pub const include = "WebCore/AbortSignal.h"; + pub const name = "JSC::AbortSignal"; + pub const namespace = "JSC"; + + pub fn addListener( + this: *AbortSignal, + ctx: ?*anyopaque, + callback: *const fn (?*anyopaque, JSValue) callconv(.C) void, + ) *AbortSignal { + return cppFn("addListener", .{ this, ctx, callback }); + } + pub fn signal( + this: *AbortSignal, + reason: JSValue, + ) *AbortSignal { + return cppFn("signal", .{ this, reason }); + } + + pub fn aborted(this: *AbortSignal) bool { + return cppFn("aborted", .{this}); + } + + pub fn abortReason(this: *AbortSignal) JSValue { + return cppFn("abortReason", .{this}); + } + + pub fn ref( + this: *AbortSignal, + ) *AbortSignal { + return cppFn("ref", .{this}); + } + + pub fn unref( + this: *AbortSignal, + ) *AbortSignal { + return cppFn("unref", .{this}); + } + + pub fn fromJS(value: JSValue) ?*AbortSignal { + return cppFn("fromJS", .{value}); + } + + pub fn createAbortError(message: *const ZigString, code: *const ZigString, global: *JSGlobalObject) JSValue { + return cppFn("createAbortError", .{ message, code, global }); + } + + pub fn createTimeoutError(message: *const ZigString, code: *const ZigString, global: *JSGlobalObject) JSValue { + return cppFn("createTimeoutError", .{ message, code, global }); + } + + pub const Extern = [_][]const u8{ + "createAbortError", + "createTimeoutError", + "ref", + "unref", + "signal", + "abortReason", + "aborted", + "addListener", + "fromJS", + }; +}; + pub const JSPromise = extern struct { pub const shim = Shimmer("JSC", "JSPromise", @This()); bytes: shim.Bytes, diff --git a/src/bun.js/bindings/headers-cpp.h b/src/bun.js/bindings/headers-cpp.h index 4dc7a2143..d0abc7db0 100644 --- a/src/bun.js/bindings/headers-cpp.h +++ b/src/bun.js/bindings/headers-cpp.h @@ -1,4 +1,4 @@ -//-- AUTOGENERATED FILE -- 1676266700 +//-- AUTOGENERATED FILE -- 1676470760 // clang-format off #pragma once @@ -56,6 +56,14 @@ extern "C" const size_t JSC__JSString_object_align_ = alignof(JSC::JSString); extern "C" const size_t JSC__JSModuleLoader_object_size_ = sizeof(JSC::JSModuleLoader); extern "C" const size_t JSC__JSModuleLoader_object_align_ = alignof(JSC::JSModuleLoader); +#ifndef INCLUDED_WebCore_AbortSignal_h +#define INCLUDED_WebCore_AbortSignal_h +#include "WebCore/AbortSignal.h" +#endif + +extern "C" const size_t JSC__AbortSignal_object_size_ = sizeof(JSC::AbortSignal); +extern "C" const size_t JSC__AbortSignal_object_align_ = alignof(JSC::AbortSignal); + #ifndef INCLUDED_JavaScriptCore_JSPromise_h #define INCLUDED_JavaScriptCore_JSPromise_h #include "JavaScriptCore/JSPromise.h" @@ -160,8 +168,8 @@ extern "C" const size_t Zig__ConsoleClient_object_align_ = alignof(Zig::ConsoleC extern "C" const size_t Bun__Timer_object_size_ = sizeof(Bun__Timer); extern "C" const size_t Bun__Timer_object_align_ = alignof(Bun__Timer); -const size_t sizes[39] = {sizeof(JSC::JSObject), sizeof(WebCore::DOMURL), sizeof(WebCore::DOMFormData), sizeof(WebCore::FetchHeaders), sizeof(SystemError), sizeof(JSC::JSCell), sizeof(JSC::JSString), sizeof(JSC::JSModuleLoader), sizeof(JSC::JSPromise), sizeof(JSC::JSInternalPromise), sizeof(JSC::JSFunction), sizeof(JSC::JSGlobalObject), sizeof(JSC::JSValue), sizeof(JSC::Exception), sizeof(JSC::VM), sizeof(JSC::ThrowScope), sizeof(JSC::CatchScope), sizeof(FFI__ptr), sizeof(Reader__u8), sizeof(Reader__u16), sizeof(Reader__u32), sizeof(Reader__ptr), sizeof(Reader__i8), sizeof(Reader__i16), sizeof(Reader__i32), sizeof(Reader__f32), sizeof(Reader__f64), sizeof(Reader__i64), sizeof(Reader__u64), sizeof(Reader__intptr), sizeof(Crypto__getRandomValues), sizeof(Crypto__randomUUID), sizeof(Crypto__timingSafeEqual), sizeof(Zig::GlobalObject), sizeof(Bun__Path), sizeof(ArrayBufferSink), sizeof(HTTPSResponseSink), sizeof(HTTPResponseSink), sizeof(FileSink)}; +const size_t sizes[40] = {sizeof(JSC::JSObject), sizeof(WebCore::DOMURL), sizeof(WebCore::DOMFormData), sizeof(WebCore::FetchHeaders), sizeof(SystemError), sizeof(JSC::JSCell), sizeof(JSC::JSString), sizeof(JSC::JSModuleLoader), sizeof(JSC::AbortSignal), sizeof(JSC::JSPromise), sizeof(JSC::JSInternalPromise), sizeof(JSC::JSFunction), sizeof(JSC::JSGlobalObject), sizeof(JSC::JSValue), sizeof(JSC::Exception), sizeof(JSC::VM), sizeof(JSC::ThrowScope), sizeof(JSC::CatchScope), sizeof(FFI__ptr), sizeof(Reader__u8), sizeof(Reader__u16), sizeof(Reader__u32), sizeof(Reader__ptr), sizeof(Reader__i8), sizeof(Reader__i16), sizeof(Reader__i32), sizeof(Reader__f32), sizeof(Reader__f64), sizeof(Reader__i64), sizeof(Reader__u64), sizeof(Reader__intptr), sizeof(Crypto__getRandomValues), sizeof(Crypto__randomUUID), sizeof(Crypto__timingSafeEqual), sizeof(Zig::GlobalObject), sizeof(Bun__Path), sizeof(ArrayBufferSink), sizeof(HTTPSResponseSink), sizeof(HTTPResponseSink), sizeof(FileSink)}; -const char* names[39] = {"JSC__JSObject", "WebCore__DOMURL", "WebCore__DOMFormData", "WebCore__FetchHeaders", "SystemError", "JSC__JSCell", "JSC__JSString", "JSC__JSModuleLoader", "JSC__JSPromise", "JSC__JSInternalPromise", "JSC__JSFunction", "JSC__JSGlobalObject", "JSC__JSValue", "JSC__Exception", "JSC__VM", "JSC__ThrowScope", "JSC__CatchScope", "FFI__ptr", "Reader__u8", "Reader__u16", "Reader__u32", "Reader__ptr", "Reader__i8", "Reader__i16", "Reader__i32", "Reader__f32", "Reader__f64", "Reader__i64", "Reader__u64", "Reader__intptr", "Crypto__getRandomValues", "Crypto__randomUUID", "Crypto__timingSafeEqual", "Zig__GlobalObject", "Bun__Path", "ArrayBufferSink", "HTTPSResponseSink", "HTTPResponseSink", "FileSink"}; +const char* names[40] = {"JSC__JSObject", "WebCore__DOMURL", "WebCore__DOMFormData", "WebCore__FetchHeaders", "SystemError", "JSC__JSCell", "JSC__JSString", "JSC__JSModuleLoader", "JSC__AbortSignal", "JSC__JSPromise", "JSC__JSInternalPromise", "JSC__JSFunction", "JSC__JSGlobalObject", "JSC__JSValue", "JSC__Exception", "JSC__VM", "JSC__ThrowScope", "JSC__CatchScope", "FFI__ptr", "Reader__u8", "Reader__u16", "Reader__u32", "Reader__ptr", "Reader__i8", "Reader__i16", "Reader__i32", "Reader__f32", "Reader__f64", "Reader__i64", "Reader__u64", "Reader__intptr", "Crypto__getRandomValues", "Crypto__randomUUID", "Crypto__timingSafeEqual", "Zig__GlobalObject", "Bun__Path", "ArrayBufferSink", "HTTPSResponseSink", "HTTPResponseSink", "FileSink"}; -const size_t aligns[39] = {alignof(JSC::JSObject), alignof(WebCore::DOMURL), alignof(WebCore::DOMFormData), alignof(WebCore::FetchHeaders), alignof(SystemError), alignof(JSC::JSCell), alignof(JSC::JSString), alignof(JSC::JSModuleLoader), alignof(JSC::JSPromise), alignof(JSC::JSInternalPromise), alignof(JSC::JSFunction), alignof(JSC::JSGlobalObject), alignof(JSC::JSValue), alignof(JSC::Exception), alignof(JSC::VM), alignof(JSC::ThrowScope), alignof(JSC::CatchScope), alignof(FFI__ptr), alignof(Reader__u8), alignof(Reader__u16), alignof(Reader__u32), alignof(Reader__ptr), alignof(Reader__i8), alignof(Reader__i16), alignof(Reader__i32), alignof(Reader__f32), alignof(Reader__f64), alignof(Reader__i64), alignof(Reader__u64), alignof(Reader__intptr), alignof(Crypto__getRandomValues), alignof(Crypto__randomUUID), alignof(Crypto__timingSafeEqual), alignof(Zig::GlobalObject), alignof(Bun__Path), alignof(ArrayBufferSink), alignof(HTTPSResponseSink), alignof(HTTPResponseSink), alignof(FileSink)}; +const size_t aligns[40] = {alignof(JSC::JSObject), alignof(WebCore::DOMURL), alignof(WebCore::DOMFormData), alignof(WebCore::FetchHeaders), alignof(SystemError), alignof(JSC::JSCell), alignof(JSC::JSString), alignof(JSC::JSModuleLoader), alignof(JSC::AbortSignal), alignof(JSC::JSPromise), alignof(JSC::JSInternalPromise), alignof(JSC::JSFunction), alignof(JSC::JSGlobalObject), alignof(JSC::JSValue), alignof(JSC::Exception), alignof(JSC::VM), alignof(JSC::ThrowScope), alignof(JSC::CatchScope), alignof(FFI__ptr), alignof(Reader__u8), alignof(Reader__u16), alignof(Reader__u32), alignof(Reader__ptr), alignof(Reader__i8), alignof(Reader__i16), alignof(Reader__i32), alignof(Reader__f32), alignof(Reader__f64), alignof(Reader__i64), alignof(Reader__u64), alignof(Reader__intptr), alignof(Crypto__getRandomValues), alignof(Crypto__randomUUID), alignof(Crypto__timingSafeEqual), alignof(Zig::GlobalObject), alignof(Bun__Path), alignof(ArrayBufferSink), alignof(HTTPSResponseSink), alignof(HTTPResponseSink), alignof(FileSink)}; diff --git a/src/bun.js/bindings/headers.h b/src/bun.js/bindings/headers.h index 159a7acbd..59450ecf1 100644 --- a/src/bun.js/bindings/headers.h +++ b/src/bun.js/bindings/headers.h @@ -1,5 +1,5 @@ // clang-format off -//-- AUTOGENERATED FILE -- 1676266700 +//-- AUTOGENERATED FILE -- 1676470760 #pragma once #include <stddef.h> @@ -55,6 +55,7 @@ typedef void* JSClassRef; typedef bJSC__JSObject JSC__JSObject; // JSC::JSObject typedef WebSocketClient WebSocketClient; typedef WebSocketHTTPSClient WebSocketHTTPSClient; + typedef struct JSC__AbortSignal JSC__AbortSignal; // JSC::AbortSignal typedef JSClassRef JSClassRef; typedef bJSC__VM JSC__VM; // JSC::VM typedef Bun__ArrayBuffer Bun__ArrayBuffer; @@ -85,6 +86,7 @@ typedef void* JSClassRef; class JSGlobalObject; class JSPromise; class Exception; + class AbortSignal; class JSString; class JSInternalPromise; class CatchScope; @@ -116,6 +118,7 @@ typedef void* JSClassRef; using JSC__JSGlobalObject = JSC::JSGlobalObject; using JSC__JSPromise = JSC::JSPromise; using JSC__Exception = JSC::Exception; + using JSC__AbortSignal = JSC::AbortSignal; using JSC__JSString = JSC::JSString; using JSC__JSInternalPromise = JSC::JSInternalPromise; using JSC__CatchScope = JSC::CatchScope; @@ -202,6 +205,18 @@ CPP_DECL void JSC__JSString__toZigString(JSC__JSString* arg0, JSC__JSGlobalObjec CPP_DECL JSC__JSValue JSC__JSModuleLoader__evaluate(JSC__JSGlobalObject* arg0, const unsigned char* arg1, size_t arg2, const unsigned char* arg3, size_t arg4, const unsigned char* arg5, size_t arg6, JSC__JSValue JSValue7, JSC__JSValue* arg8); CPP_DECL JSC__JSInternalPromise* JSC__JSModuleLoader__loadAndEvaluateModule(JSC__JSGlobalObject* arg0, const ZigString* arg1); +#pragma mark - JSC::AbortSignal + +CPP_DECL bool JSC__AbortSignal__aborted(JSC__AbortSignal* arg0); +CPP_DECL JSC__JSValue JSC__AbortSignal__abortReason(JSC__AbortSignal* arg0); +CPP_DECL JSC__AbortSignal* JSC__AbortSignal__addListener(JSC__AbortSignal* arg0, void* arg1, void(* ArgFn2)(void* arg0, JSC__JSValue JSValue1)) __attribute__((nonnull (2))); +CPP_DECL JSC__JSValue JSC__AbortSignal__createAbortError(const ZigString* arg0, const ZigString* arg1, JSC__JSGlobalObject* arg2); +CPP_DECL JSC__JSValue JSC__AbortSignal__createTimeoutError(const ZigString* arg0, const ZigString* arg1, JSC__JSGlobalObject* arg2); +CPP_DECL JSC__AbortSignal* JSC__AbortSignal__fromJS(JSC__JSValue JSValue0); +CPP_DECL JSC__AbortSignal* JSC__AbortSignal__ref(JSC__AbortSignal* arg0); +CPP_DECL JSC__AbortSignal* JSC__AbortSignal__signal(JSC__AbortSignal* arg0, JSC__JSValue JSValue1); +CPP_DECL JSC__AbortSignal* JSC__AbortSignal__unref(JSC__AbortSignal* arg0); + #pragma mark - JSC::JSPromise CPP_DECL JSC__JSValue JSC__JSPromise__asValue(JSC__JSPromise* arg0, JSC__JSGlobalObject* arg1); diff --git a/src/bun.js/bindings/headers.zig b/src/bun.js/bindings/headers.zig index 756a08bcc..9f2e1580d 100644 --- a/src/bun.js/bindings/headers.zig +++ b/src/bun.js/bindings/headers.zig @@ -135,6 +135,15 @@ pub extern fn JSC__JSString__toObject(arg0: [*c]bindings.JSString, arg1: *bindin pub extern fn JSC__JSString__toZigString(arg0: [*c]bindings.JSString, arg1: *bindings.JSGlobalObject, arg2: [*c]ZigString) void; pub extern fn JSC__JSModuleLoader__evaluate(arg0: *bindings.JSGlobalObject, arg1: [*c]const u8, arg2: usize, arg3: [*c]const u8, arg4: usize, arg5: [*c]const u8, arg6: usize, JSValue7: JSC__JSValue, arg8: [*c]bindings.JSValue) JSC__JSValue; pub extern fn JSC__JSModuleLoader__loadAndEvaluateModule(arg0: *bindings.JSGlobalObject, arg1: [*c]const ZigString) [*c]bindings.JSInternalPromise; +pub extern fn JSC__AbortSignal__aborted(arg0: ?*bindings.AbortSignal) bool; +pub extern fn JSC__AbortSignal__abortReason(arg0: ?*bindings.AbortSignal) JSC__JSValue; +pub extern fn JSC__AbortSignal__addListener(arg0: ?*bindings.AbortSignal, arg1: ?*anyopaque, ArgFn2: ?*const fn (?*anyopaque, JSC__JSValue) callconv(.C) void) ?*bindings.AbortSignal; +pub extern fn JSC__AbortSignal__createAbortError(arg0: [*c]const ZigString, arg1: [*c]const ZigString, arg2: *bindings.JSGlobalObject) JSC__JSValue; +pub extern fn JSC__AbortSignal__createTimeoutError(arg0: [*c]const ZigString, arg1: [*c]const ZigString, arg2: *bindings.JSGlobalObject) JSC__JSValue; +pub extern fn JSC__AbortSignal__fromJS(JSValue0: JSC__JSValue) ?*bindings.AbortSignal; +pub extern fn JSC__AbortSignal__ref(arg0: ?*bindings.AbortSignal) ?*bindings.AbortSignal; +pub extern fn JSC__AbortSignal__signal(arg0: ?*bindings.AbortSignal, JSValue1: JSC__JSValue) ?*bindings.AbortSignal; +pub extern fn JSC__AbortSignal__unref(arg0: ?*bindings.AbortSignal) ?*bindings.AbortSignal; pub extern fn JSC__JSPromise__asValue(arg0: ?*bindings.JSPromise, arg1: *bindings.JSGlobalObject) JSC__JSValue; pub extern fn JSC__JSPromise__create(arg0: *bindings.JSGlobalObject) ?*bindings.JSPromise; pub extern fn JSC__JSPromise__isHandled(arg0: [*c]const JSC__JSPromise, arg1: *bindings.VM) bool; diff --git a/src/bun.js/bindings/sizes.zig b/src/bun.js/bindings/sizes.zig index 795159e49..b1b9c1679 100644 --- a/src/bun.js/bindings/sizes.zig +++ b/src/bun.js/bindings/sizes.zig @@ -78,4 +78,4 @@ pub const Bun_CallFrame__argumentCountIncludingThis = 4; pub const Bun_CallFrame__thisArgument = 5; pub const Bun_CallFrame__firstArgument = 6; pub const Bun_CallFrame__size = 8; -pub const Bun_CallFrame__align = 8; +pub const Bun_CallFrame__align = 8;
\ No newline at end of file diff --git a/src/bun.js/bindings/webcore/AbortSignal.cpp b/src/bun.js/bindings/webcore/AbortSignal.cpp index aa4143ebd..132ecefca 100644 --- a/src/bun.js/bindings/webcore/AbortSignal.cpp +++ b/src/bun.js/bindings/webcore/AbortSignal.cpp @@ -105,6 +105,12 @@ void AbortSignal::signalAbort(JSC::JSValue reason) for (auto& algorithm : algorithms) algorithm(reason); + auto callbacks = std::exchange(m_native_callbacks, {}); + for (auto callback : callbacks) { + const auto [ ctx, func ] = callback; + func(ctx, JSC::JSValue::encode(reason)); + } + // 5. Fire an event named abort at signal. dispatchEvent(Event::create(eventNames().abortEvent, Event::CanBubble::No, Event::IsCancelable::No)); } diff --git a/src/bun.js/bindings/webcore/AbortSignal.h b/src/bun.js/bindings/webcore/AbortSignal.h index 05e64ca82..b0c59daae 100644 --- a/src/bun.js/bindings/webcore/AbortSignal.h +++ b/src/bun.js/bindings/webcore/AbortSignal.h @@ -65,6 +65,7 @@ public: using Algorithm = Function<void(JSValue)>; void addAlgorithm(Algorithm&& algorithm) { m_algorithms.append(WTFMove(algorithm)); } + void addNativeCallback(std::tuple<void*, void (*)(void*, JSC::EncodedJSValue)> callback) { m_native_callbacks.append(callback); } bool isFollowingSignal() const { return !!m_followingSignal; } @@ -86,6 +87,7 @@ private: bool m_aborted { false }; Vector<Algorithm> m_algorithms; + Vector<std::tuple<void*, void (*)(void*, JSC::EncodedJSValue)>> m_native_callbacks; WeakPtr<AbortSignal> m_followingSignal; JSValueInWrappedObject m_reason; bool m_hasActiveTimeoutTimer { false }; diff --git a/src/bun.js/event_loop.zig b/src/bun.js/event_loop.zig index 8dbf5abfd..9c2627fda 100644 --- a/src/bun.js/event_loop.zig +++ b/src/bun.js/event_loop.zig @@ -173,6 +173,7 @@ pub const AnyTask = struct { } }; + pub const CppTask = opaque { extern fn Bun__performTask(globalObject: *JSGlobalObject, task: *CppTask) void; pub fn run(this: *CppTask, global: *JSGlobalObject) void { diff --git a/src/bun.js/javascript.zig b/src/bun.js/javascript.zig index b926c4ee9..a5ef4a44a 100644 --- a/src/bun.js/javascript.zig +++ b/src/bun.js/javascript.zig @@ -1150,7 +1150,7 @@ pub const VirtualMachine = struct { const after_namespace = if (namespace.len == 0) specifier else - specifier.substring(namespace.len + 1); + specifier.substring(namespace.len + 1, specifier.len); if (plugin_runner.onResolveJSC(ZigString.init(namespace), after_namespace, source, .bun)) |resolved_path| { res.* = resolved_path; diff --git a/src/bun.js/webcore/response.zig b/src/bun.js/webcore/response.zig index 2c3b1ee31..725a4e64c 100644 --- a/src/bun.js/webcore/response.zig +++ b/src/bun.js/webcore/response.zig @@ -688,6 +688,31 @@ pub const Fetch = struct { } pub fn onReject(this: *FetchTasklet) JSValue { + if (this.result.isTimeout()) { + //Timeout with reason + if (this.result.reason) |exception| { + if (!exception.isEmptyOrUndefinedOrNull()) { + return exception; + } + } + //Timeout without reason + const exception = JSC.AbortSignal.createTimeoutError(JSC.ZigString.static("The operation timed out"), &JSC.ZigString.Empty, this.global_this); + return exception; + } + + if (this.result.isAbort()) { + //Abort can be TimeoutError (AbortSignal.timeout(ms)) or AbortError so we need to detect + if (this.result.reason) |exception| { + if (!exception.isEmptyOrUndefinedOrNull()) { + return exception; + } + } + + //Abort without reason + const exception = JSC.AbortSignal.createAbortError(JSC.ZigString.static("The user aborted a request"), &JSC.ZigString.Empty, this.global_this); + return exception; + } + const fetch_error = JSC.SystemError{ .code = ZigString.init(@errorName(this.result.fail)), .message = ZigString.init("fetch() failed"), @@ -788,7 +813,7 @@ pub const Fetch = struct { FetchTasklet.callback, ).init( fetch_tasklet, - ), proxy); + ), proxy, fetch_options.signal); if (!fetch_options.follow_redirects) { fetch_tasklet.http.?.client.remaining_redirect_count = 0; @@ -800,7 +825,7 @@ pub const Fetch = struct { return fetch_tasklet; } - const FetchOptions = struct { method: Method, headers: Headers, body: AnyBlob, timeout: usize, disable_timeout: bool, disable_keepalive: bool, url: ZigURL, verbose: bool = false, follow_redirects: bool = true, proxy: ?ZigURL = null, url_proxy_buffer: []const u8 = "" }; + const FetchOptions = struct { method: Method, headers: Headers, body: AnyBlob, timeout: usize, disable_timeout: bool, disable_keepalive: bool, url: ZigURL, verbose: bool = false, follow_redirects: bool = true, proxy: ?ZigURL = null, url_proxy_buffer: []const u8 = "", signal: ?*JSC.AbortSignal = null, globalThis: ?*JSGlobalObject }; pub fn queue( allocator: std.mem.Allocator, @@ -862,6 +887,8 @@ pub const Fetch = struct { var verbose = false; var proxy: ?ZigURL = null; var follow_redirects = true; + var signal: ?*JSC.AbortSignal = null; + var url_proxy_buffer: []const u8 = undefined; if (first_arg.as(Request)) |request| { @@ -929,6 +956,12 @@ pub const Fetch = struct { if (options.get(globalThis, "verbose")) |verb| { verbose = verb.toBoolean(); } + if (options.get(globalThis, "signal")) |signal_arg| { + if (signal_arg.as(JSC.AbortSignal)) |signal_| { + _ = signal_.ref(); + signal = signal_; + } + } if (options.get(globalThis, "proxy")) |proxy_arg| { if (!proxy_arg.isUndefined()) { if (proxy_arg.isNull()) { @@ -1040,6 +1073,12 @@ pub const Fetch = struct { if (options.get(globalThis, "verbose")) |verb| { verbose = verb.toBoolean(); } + if (options.get(globalThis, "signal")) |signal_arg| { + if (signal_arg.as(JSC.AbortSignal)) |signal_| { + _ = signal_.ref(); + signal = signal_; + } + } if (options.get(globalThis, "proxy")) |proxy_arg| { if (!proxy_arg.isUndefined()) { var proxy_str = proxy_arg.toStringOrNull(globalThis) orelse return null; @@ -1159,7 +1198,7 @@ pub const Fetch = struct { globalThis, .{ .method = method, .url = url, .headers = headers orelse Headers{ .allocator = bun.default_allocator, - }, .body = body, .timeout = std.time.ns_per_hour, .disable_keepalive = disable_keepalive, .disable_timeout = disable_timeout, .follow_redirects = follow_redirects, .verbose = verbose, .proxy = proxy, .url_proxy_buffer = url_proxy_buffer }, + }, .body = body, .timeout = std.time.ns_per_hour, .disable_keepalive = disable_keepalive, .disable_timeout = disable_timeout, .follow_redirects = follow_redirects, .verbose = verbose, .proxy = proxy, .url_proxy_buffer = url_proxy_buffer, .signal = signal, .globalThis = globalThis }, JSC.JSValue.fromRef(deferred_promise), ) catch unreachable; return deferred_promise; |