- DIFFERENCES FROM ECMASCRIPT PROMISES
- AVOID MULTIPLES
- DIFFERENCES FROM Promises ET AL.
- EVENT LOOPS
- MEMORY LEAK DETECTION
- KNOWN ISSUES
- SEE ALSO
Promise::XS - Fast promises in Perl
use Promise::XS (); my $deferred = Promise::XS::deferred(); # Do one of these once you have the result of your operation: $deferred->resolve( 'foo', 'bar' ); $deferred->reject( 'oh', 'no!' ); # Give this to your caller: my $promise = $deferred->promise();
The following aggregator functions are exposed:
# Resolves with a list of arrayrefs, one per promise. # Rejects with the results from the first rejected promise. my $all_p = Promise::XS::all( $promise1, $promise2, .. ); # Resolves/rejects with the results from the first # resolved or rejected promise. my $race_p = Promise::XS::race( $promise3, $promise4, .. );
For compatibility with preexisting libraries,
all() may also be called as
The following also exist:
my $pre_resolved_promise = Promise::XS::resolved('already', 'done'); my $pre_rejected_promise = Promise::XS::rejected('it’s', 'bad');
Promise::XS’s static functions may be exported at load time, e.g.,
use Promise::XS qw(deferred).
This module exposes a Promise interface with its major parts implemented in XS for speed. It is a fork and refactor of AnyEvent::XSPromises. That module’s interface, a “bare-bones” subset of that from Promises, is retained.
This module is stable, well-tested, and suitable for production use.
This library is built for compatibility with pre-existing Perl promise libraries. It thus exhibits some salient differences from how ECMAScript promises work:
resolve()method of deferred objects nor the
resolved()convenience function define behavior when given a promise object.
race()functions accept a list of promises, not a “scalar-array-thing” (ECMAScript “arrays” being what in Perl we call “array references”). So whereas in ECMAScript you do:
Promise.all( [ promise1, promise2 ] );
… in this library it’s:
Promise::XS::all( $promise1, $promise2 );
Promise resolutions and rejections may contain multiple values. (But see "AVOID MULTIPLES" below.)
See Promise::ES6 for an interface that imitates ECMAScript promises more closely.
For compatibility with preexisting Perl promise libraries, Promise::XS allows a promise to resolve or reject with multiple values. This behavior, while eminently “perlish”, allows for some weird cases where the relevant standards don’t apply: for example, what happens if multiple promises are returned from a promise callback? Or even just a single promise plus extra returns?
Promise::XS tries to help you catch such cases by throwing a warning if multiple return values from a callback contain a promise as the first member. For best results, though—and consistency with promise implementations outside Perl—resolve/reject all promises with single values.
DIFFERENCES FROM Promises ET AL.
Promise rejections fulfill the same role in asynchronous code that exceptions do in synchronous code. Perl helpfully warns (under the
warnings pragma, anyhow) when you
die(undef) since an uninitialized value isn’t useful as an error report and likely indicates a problem.
Promise::XS mimics this behavior by warning if a rejection value list lacks a defined value. This can happen if the value list is either empty or contains exclusively uninitialized values.
This module implements ECMAScript’s
finally() interface, which differs from that in some other Perl promise implementations.
Given the following …
my $new = $p->finally( $callback );
$callbackreceives no arguments.
$callbackreturns anything but a single, rejected promise,
$newhas the same status as
$callbackthrows, or if it returns a single, rejected promise,
$newis rejected with the relevant value(s).
To achieve full Promises/A+ compliance it’s necessary to integrate with an event loop interface. This library supports three such interfaces:
Note that all three of the above are event loop interfaces. They aren’t event loops themselves, but abstractions over various event loops. See each one’s documentation for details about supported event loops.
Any promise created while
$Promise::XS::DETECT_MEMORY_LEAKS is truthy will throw a warning if it survives until global destruction.
You can re-bless a Promise::XS::Promise instance into a different class, and
finally() will assign their newly-created promise into that other class. (It follows that the other class must subclass Promise::XS::Promise.) This can be useful, e.g., for implementing mid-flight controls like cancellation.
race()should ideally be implemented in XS.
Interpreter-based threads may or may not work.
This module interacts badly with Perl’s fork() implementation on Windows. There may be a workaround possible, but none is implemented for now.
Besides AnyEvent::XSPromises and Promises, you may like Promise::ES6, which mimics ECMAScript’s “Promise” class as much as possible. It can even (experimentally) use this module as a backend, which helps but is still significantly slower than using this module directly.