@ngxs-labs/select-snapshot
Advanced tools
Comparing version 2.0.0 to 2.0.1
{ | ||
"$schema": "../node_modules/ng-packagr/package.schema.json", | ||
"name": "@ngxs-labs/select-snapshot", | ||
"version": "2.0.0", | ||
"version": "2.0.1", | ||
"repository": { | ||
@@ -6,0 +6,0 @@ "type": "git", |
@@ -13,2 +13,11 @@ <p align="center"> | ||
## Table of Contents | ||
- [Install](#📦-install) | ||
- [Usage](#🔨-usage) | ||
- [API](#api) | ||
- [SelectSnapshot](#selectsnapshot) | ||
- [ViewSelectSnapshot](#viewselectsnapshot) | ||
- [Summary](#summary) | ||
## 📦 Install | ||
@@ -39,23 +48,27 @@ | ||
### Selecting snapshot | ||
## API | ||
The `@SelectSnapshot` is just a simple decorator same as `@Select`. It allows you to decorate properties of your classes applying new getter and lets you to avoid injecting `Store` class everywhere. Simple example, let's create some tiny `pandas` state: | ||
There are 2 decorators exposed publicly. These are `@SelectSnapshot` and `@ViewSelectSnapshot`. They can be used to decorate class properties. | ||
```typescript | ||
import { State, Action, StateContext } from '@ngxs/store'; | ||
### SelectSnapshot | ||
class AddPanda { | ||
static type = '[Pandas] Add panda'; | ||
constructor(public panda: string) {} | ||
} | ||
`@SelectSnapshot` decorator behaves the same as the `@Select` decorator. The only difference is `@SelectSnapshot` decorated property will always return the current state value whereas `@Select` decorated property returns an `Observable`. Let's look at the following example: | ||
@State<string[]>({ | ||
name: 'pandas', | ||
defaults: [], | ||
}) | ||
export class PandasState { | ||
@Action(AddPanda) | ||
addPanda(ctx: StateContext<string[]>, action: AddPanda): void { | ||
const pandas = ctx.getState(); | ||
ctx.setState([...pandas, action.panda]); | ||
```ts | ||
import { SelectSnapshot } from '@ngxs-labs/select-snapshot'; | ||
@Injectable() | ||
export class TokenInterceptor { | ||
@SelectSnapshot(AuthState.token) token: string | null; | ||
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> { | ||
if (this.token) { | ||
req = req.clone({ | ||
setHeaders: { | ||
Authorization: `Bearer ${this.token}`, | ||
}, | ||
}); | ||
} | ||
return next.handle(req); | ||
} | ||
@@ -65,19 +78,46 @@ } | ||
Assume you've provided this state into your root `NgxsModule` and want already to try the `@SelectSnapshot` decorator: | ||
As you may notice we don't have to inject the `Store` class and invoke the `selectSnapshot` on it. | ||
```typescript | ||
import { Component } from '@angular/core'; | ||
import { SelectSnapshot } from '@ngxs-labs/select-snapshot'; | ||
### ViewSelectSnapshot | ||
import { PandasState } from './pandas.state'; | ||
`@ViewSelectSnapshot` is a decorator that should decorate class properties that are used in templates (e.g. _renderable_ or passed as _bindings_). Given the following example: | ||
```ts | ||
@Component({ | ||
selector: 'app-root', | ||
template: '<app-panda *ngFor="let panda of pandas" [panda]="panda"></app-panda>', | ||
selector: 'app-progress', | ||
template: ` | ||
<div> | ||
<div [style.width.%]="progress"></div> | ||
</div> | ||
`, | ||
changeDetection: ChangeDetectionStrategy.OnPush, | ||
}) | ||
export class AppComponent { | ||
@SelectSnapshot(PandasState) pandas: string[]; | ||
export class ProgressComponent { | ||
// 🚫 Do not use `SelectSnapshot` since `progress` is used in the template. | ||
@SelectSnapshot(ProgressState.getProgress) progress: number; | ||
} | ||
``` | ||
The `@SelectSnapshot` decorator has the same API as the `@Select` decorator. It accepts state class, selector function, string or nothing as an argument. | ||
Why? Because if the `progress` state gets updated then Angular has to check that view and update it. This view will not get updated because it's marked as `OnPush`, which means it's constantly in `CheckOnce` state. How to make the above example work? | ||
```ts | ||
@Component({ | ||
selector: 'app-progress', | ||
template: ` | ||
<div> | ||
<div [style.width.%]="progress"></div> | ||
</div> | ||
`, | ||
changeDetection: ChangeDetectionStrategy.OnPush, | ||
}) | ||
export class ProgressComponent { | ||
// ✔️ Our view will be checked and updated. | ||
@ViewSelectSnapshot(ProgressState.getProgress) progress: number; | ||
} | ||
``` | ||
How does it work? The `@ViewSelectSnapshot` decorator calls `markForCheck()` under the hood when the `progress` state gets updated. | ||
## Summary | ||
We have looked at several examples of using both decorators. Consider to use the `@SelectSnapshot` if decorated properties are not used in templates! Consider to use the `@ViewSelectSnapshot` if decorated properties are used in templates (e.g. _renderable_ or passed as _bindings_). |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
188986
121