[英]How to use JSObjectMakeDeferredPromise to call a function in JavaScript from Swift that returns a promise
我希望能夠從返回承諾的 JSContext 調用函數。 JSObjectMakeDeferredPromise 似乎是這樣做的機制,但文檔太少,我不確定如何去做。
任何人都可以提供一個在 JSContext 中調用一個返回承諾的函數的例子嗎?
WebKit 是一個開源項目。 我發現了一個與該功能相關的問題。
這個函數更喜歡為未處理的承諾拒絕拋出異常。
所以你不能使用那個函數來返回一個承諾。
但是
JavaScriptCore 支持 Promise 關鍵字。 我使用 Xcode 11.4.1 在 macOS 上運行此腳本。 這很好用。
const promiseA = new Promise( (resolve, reject) => {
emulator.downloadWithHandler( (response) => {
var isFinish = response["isFinish"];
var isCancelled = response["isCancelled"];
var date = response["date"];
console.log("isFinish: " + isFinish);
console.log("isCancelled: " + isCancelled);
console.log("date: " + date);
if (isFinish || isCancelled) {
resolve(date);
}
});
});
emulator.downloadWithHandler
是一個本地回調,它會在某個時候在后台 DispatchQueue 上返回。 如果您想使用檢索該承諾並保留它。 調用context.objectForKeyedSubscript("promiseA")
並使用JSManagedValue
包裝它。
保留Promise
的引用並沒有多大用處。 更重要的是如何訪問JSContext
的變量和函數。
你可以調用 JSContext 的evaluateScript(_:)
。 如果您在腳本返回后保留上下文,則該上下文不會取消初始化並且可以使用。 從上下文中獲取對象,然后使用 JSValue 的invokeMethod(_:withArguments:)
或call(withArguments:)
也可以工作。
NSHipster 有一篇關於該框架的精彩文章。 你可以參考一下。
在我檢查文檔和 iOS 13+ 新 API 之后。 有什么可以確認的。 也就是說你可以使用JSObjectMakeDeferredPromise
創建Promise
,這是 C 的方式。 為方便起見,我通過 Swift 方式創建了所需的函數並導出到 C。所以答案是:
let context = JSContext()
var ref = context.jsGlobalContextRef
context.evaluateScript("function resolve(value) { console.log(value); };")
var resolve = context.objectForKeyedSubscript("resolve")?.jsValueRef
context.evaluateScript("function reject(reason) { console.log(reason); };")
var reject = context.objectForKeyedSubscript("reject")?.jsValueRef
var exception: JSValueRef?
var promise = JSObjectMakeDeferredPromise(ref, &resolve, &reject, &exception)
(lldb) po promise
▿ Optional<OpaquePointer>
▿ some : 0x000000010c74ae78
- _rawValue : (Opaque Value)
(lldb) p promise
(JSObjectRef?) $R4 = 0x000000010c74ae78
我不想再深入。 那只是意味着您可以將 JavaScriptCore 與 C 接口一起使用。 並且JSValue
有 iOS 13+ 新的 C 風格的 init 方法, .init(newPromiseIn:fromExecutor:)
。 看起來一樣,但我不太確定。
如果你堅持使用C API。 這篇文章可能會有所幫助。
PS console.log
方法是手工原生的導出日志方法。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.