Я хотел бы расширить свое приложение для работы с электронными таблицами с помощью определенных пользователем макросов. Кажется, это хорошая идея использовать javascript...
Он обнаружил «небольшую проблему» (я вообще очень не знаком с javascript)
import JavaScriptCore
let context = JSContext()!
context.exceptionHandler = { context, exception in
print("exception:", exception?.toString() ?? "")
}
context.evaluateScript(
"""
foo = function(a, b) {
return a + b
}
"""
)
context.evaluateScript("foo(1, 2)") // 3
context.objectForKeyedSubscript("foo")?.call(withArguments: [1,2]) // 3
context.evaluateScript(
"""
Foo = function() {}
Foo.foo = function(a, b) {
return a + b
}
"""
)
context.evaluateScript("Foo.foo(1, 2)") // 3
// exception. TypeError: undefined is not an object
context.objectForKeyedSubscript("Foo.foo")?.call(withArguments: [1, 2]) // Foo.foo is undefined ?????
Если Foo.foo не определен, как он мог запуститься всего на одну строку раньше?



![Безумие обратных вызовов в javascript [JS]](https://i.imgur.com/WsjO6zJb.png)


наконец-то я нашел решение...
context.objectForKeyedSubscript("Foo")?.objectForKeyedSubscript("foo")?.call(withArguments: [1, 2]) // 3
или лучше ...
extension JSContext {
func objectForKeySubscript(_ dotted: String) -> JSValue! {
var iterator = dotted.split(separator: ".").makeIterator()
var jsValue = self.objectForKeyedSubscript(iterator.next())
while let str = iterator.next() {
jsValue = jsValue?.objectForKeyedSubscript(str)
}
return jsValue
}
}
context.objectForKeySubscript("Foo.foo")?.call(withArguments: [1, 2])
и, наконец, я обнаружил, что
context.evaluateScript("Foo.foo")?.call(withArguments: [1, 2])
работает без проблем... :-)
Вы пытались .call(withArguments. Но я думаю, что это работает с Function.prototype.call(), который требует двух аргументов (объект и аргументы). Для получения дополнительной информации: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/call
Это работает
context.objectForKeyedSubscript("Foo")?.invokeMethod("foo", withArguments: [1, 2])