Доступ к структурам данных PureScript из FFI-ied JavaScript всегда плохая идея. Вы полагаетесь не только на указанный c способ написания библиотеки (без поддержки компилятора для обнаружения ошибок!), Но и на сам компилятор, поскольку представление во время выполнения может меняться от одной версии компилятора к другой (обратите внимание, что это не относится к EffectFnAff
, потому что он явно предназначен для FFI и тщательно определен как таковой, в терминах EffectFn2
).
Способ представления эффективных вычислений в FFI через Effect
:
foreign import foo :: Fn2 A (B -> Effect Unit) -> EffectFnAff Unit
Такую функцию теперь можно вызывать из JavaScript так, как вы это делаете - как f(b)
.
И если вы хотите, чтобы потребитель вашего библиотека для предоставления Aff
, то, что вы делаете, это создаете оболочку:
foreign import foo_ :: Fn2 A (B -> Effect Unit) (EffectFnAff Unit)
foo :: A -> (B -> Aff Unit) -> Aff Unit
foo a f = fromEffectFnAff $ runFn2 foo_ a (launchAff_ <<< f)
Затем вы просто экспортируете оболочку foo
, но не импорт FFI foo_
.
В некоторой связанной заметке я бы также порекомендовал покончить с EffectFnAff
, потому что вы на самом деле не запускаете ничего асинхронного, но всегда вызываете cancelerSuccess()
.
Так что вместо этого я бы порекомендовал это :
// JavaScript
exports.foo = (a, f) => a.bar(f)
-- PureScript
foreign import foo_ :: EffectFn2 A (B -> Effect Unit) Unit
foo :: A -> (B -> Aff Unit) -> Aff Unit
foo a f = liftEffect $ runEffectFn2 foo_ a (launchAff_ <<< f)
Обертка по-прежнему имеет Aff
в обоих случаях - это предполагает, что вам нужно все это вписаться в Aff
по вашим собственным причинам. В противном случае это может быть просто foo = runEffectFn2 foo_