https://github.com/snewcomer/ember-stateful-promise
Stateful wrapper for native Promises
https://github.com/snewcomer/ember-stateful-promise
ember-addon emberjs promises
Last synced: 8 months ago
JSON representation
Stateful wrapper for native Promises
- Host: GitHub
- URL: https://github.com/snewcomer/ember-stateful-promise
- Owner: snewcomer
- License: mit
- Created: 2021-10-27T02:36:19.000Z (about 4 years ago)
- Default Branch: main
- Last Pushed: 2022-02-25T03:11:55.000Z (almost 4 years ago)
- Last Synced: 2025-04-23T17:10:00.892Z (8 months ago)
- Topics: ember-addon, emberjs, promises
- Language: JavaScript
- Homepage:
- Size: 4.86 MB
- Stars: 11
- Watchers: 1
- Forks: 3
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- Contributing: CONTRIBUTING.md
- License: LICENSE.md
Awesome Lists containing this project
README
ember-stateful-promise
==============================================================================
[](https://badge.fury.io/js/ember-stateful-promise)
[](https://github.com/snewcomer/ember-stateful-promise/actions/workflows/ci.yml?query=branch%3Amain)
[](https://badge.fury.io/js/ember-stateful-promise)
[](https://emberobserver.com/addons/ember-stateful-promise)
[ember-concurrency](http://ember-concurrency.com/docs/introduction/) is the go to solution in the Ember community for tracking async action state and many other tasks around async behaviour.
`ember-stateful-promise` seeks to *simplify* with native `async/await` instead of generators and expose a few flags on a promise object for you to use. Moreover, they are tracked! This library can be used if you simply need derived state your async functions and/or need a lightweight version of ember-concurrency.
Also [ember-promise-helpers](https://github.com/fivetanley/ember-promise-helpers) is another great library if you want to calculate state from your promises. `ember-stateful-promise` is different in that is seeks to provide derived state.
Lastly, if you already use ember-concurrency but rather author with `async/await`, [ember-concurrency-async](https://github.com/chancancode/ember-concurrency-async) is available as a babel build time plugin. Again, you just need to weigh the tradeoffs (size, complexity) for your project.
## API
Supports
1. Derived state
2. Debouncing async functions
3. Cleanup of async functions wired up with `@ember/destroyable`
- `isRunning`
- `isResolved`
- `isError`
- `isCanceled`
- `performCount`
- `cancel()` // this.clickMe.cancel()
## Usage
There are a few ways to use this addon. Likely, you only need the `stateful-function` decorator. However, if you need the lower level util, we make that available as `StatefulPromise` as well.
### Decorator
```js
import Component from '@glimmer/component';
import { action } from '@ember/object';
import { statefulFunction } from 'ember-stateful-promise/decorators/stateful-function';
class MyComponent extends Component {
@statefulFunction
async clickMe() {
await fetch(url);
}
}
```
```hbs
Click
(Clicked this many times - {{this.clickMe.performCount}})
```
Note - the default behaviour out of the box is to `debounce` the action. When clicked while a promise is outstanding, the first promise will be rejected and a new promise will be created.
To throttle the function, pass `{ throttle: true }` to the decorator arguments.
```js
import Component from '@glimmer/component';
import { action } from '@ember/object';
import { statefulFunction } from 'ember-stateful-promise/decorators/stateful-function';
class MyComponent extends Component {
@statefulFunction({ throttle: true })
async clickMe() {
await fetch(url);
}
}
```
`@statefulFunction` replaces `@action` while giving you all the features of this addon!
### Stateful Promise
- Promise `interface`
```js
import { StatefulPromise } from 'ember-stateful-promise/utils/stateful-promise';
const promise = fetch(url);
let result = new StatefulPromise((resolveFn, rejectFn) => {
promise.then((data) => resolveFn(data)).catch((e) => rejectFn(e));
});
result.isRunning; // true
result.isResolved; // false
result.isError; // false
await result;
result.isRunning; // false
result.isResolved; // true
result.isError; // false
```
- `create` method with destroyable
```js
import { StatefulPromise } from 'ember-stateful-promise/utils/stateful-promise';
const promise = fetch(url);
let result = new StatefulPromise().create(this, promise);
result.isRunning; // true
result.isResolved; // false
result.isError; // false
await result;
result.isRunning; // false
result.isResolved; // true
result.isError; // false
```
```js
import { StatefulPromise } from 'ember-stateful-promise/utils/stateful-promise';
import { action } from '@ember/object';
class MyComponent extends Component {
@action
clickMe() {
const promise = fetch(url);
// Destroyable registered
let result = new StatefulPromise().create(this, (resolveFn, rejectFn) => {
promise.then((data) => resolveFn(data)).catch((e) => rejectFn(e));
});
// Component destroyed
// and then
try {
await result;
} catch (e) {
// WILL ERROR here!
}
}
}
```
Compatibility
------------------------------------------------------------------------------
* Ember.js v3.20 or above
* Ember CLI v3.20 or above
* Node.js v12 or above
Installation
------------------------------------------------------------------------------
```
ember install ember-stateful-promise
```
Contributing
------------------------------------------------------------------------------
See the [Contributing](CONTRIBUTING.md) guide for details.
License
------------------------------------------------------------------------------
This project is licensed under the [MIT License](LICENSE.md).