Skip to content

Commit d830187

Browse files
docs(): add interacting with the cache store doc
1 parent 391d0a0 commit d830187

File tree

1 file changed

+65
-22
lines changed

1 file changed

+65
-22
lines changed

content/techniques/caching.md

Lines changed: 65 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,18 @@ Caching is a great and simple **technique** that helps improve your app's perfor
44

55
#### Installation
66

7-
First install the required package:
7+
First install required packages:
88

99
```bash
10-
$ npm install --save cache-manager
10+
$ npm install cache-manager
11+
$ npm install -D @types/cache-manager
1112
```
1213

1314
#### In-memory cache
1415

15-
Nest provides a unified API for various cache storage providers. The built-in one is an in-memory data store. However, you can easily switch to a more comprehensive solution, like Redis. In order to enable caching, first import the `CacheModule` and call its `register()` method.
16+
Nest provides a unified API for various cache storage providers. The built-in one is an in-memory data store. However, you can easily switch to a more comprehensive solution, like Redis.
17+
18+
In order to enable caching, import the `CacheModule` and call its `register()` method.
1619

1720
```typescript
1821
import { CacheModule, Module } from '@nestjs/common';
@@ -25,9 +28,51 @@ import { AppController } from './app.controller';
2528
export class ApplicationModule {}
2629
```
2730

31+
#### Interacting with the Cache store
32+
33+
To interact with the cache manager instance, inject it to your class using the `CACHE_MANAGER` token, as follows:
34+
35+
```typescript
36+
constructor(@Inject(CACHE_MANAGER) private cacheManager: Cache) {}
37+
```
38+
39+
> info **Hint** The `Cache` class is imported from the `cache-manager`, while `CACHE_MANAGER` token from the `@nestjs/common` package.
40+
41+
The `get` method on the `Cache` instance (from the `cache-manager` package) is used to retrieve items from the cache. If the item does not exist in the cache, an exception will be thrown.
42+
43+
```typescript
44+
const value = this.cacheManager.get('key');
45+
```
46+
47+
To add an item to the cache, use the `set` method:
48+
49+
```typescript
50+
await this.cacheManager.set('key', 'value');
51+
```
52+
53+
You can also specify a TTL (expiration time) for this specific key, as follows:
54+
55+
```typescript
56+
await this.cacheManager.set('key', 'value', { ttl: 1000 });
57+
```
58+
59+
To remove an item from the cache, use the `del` method:
60+
61+
```typescript
62+
await this.cacheManager.del('key');
63+
```
64+
65+
To clear the entire cache, use the `reset` method:
66+
67+
```typescript
68+
await this.cacheManager.reset();
69+
```
70+
71+
#### Auto-caching responses
72+
2873
> warning **Warning** In [GraphQL](/graphql/quick-start) applications, interceptors are executed separately for each field resolver. Thus, `CacheModule` (which uses interceptors to cache responses) will not work properly.
2974
30-
Then just tie the `CacheInterceptor` where you want to cache data.
75+
To enable auto-caching responses, just tie the `CacheInterceptor` where you want to cache data.
3176

3277
```typescript
3378
@Controller()
@@ -43,8 +88,6 @@ export class AppController {
4388
> warning**Warning** Only `GET` endpoints are cached. Also, HTTP server routes that inject the native response object (`@Res()`) cannot use the Cache Interceptor. See
4489
> <a href="https://docs.nestjs.com/interceptors#response-mapping">response mapping</a> for more details.
4590
46-
#### Global cache
47-
4891
To reduce the amount of required boilerplate, you can bind `CacheInterceptor` to all endpoints globally:
4992

5093
```typescript
@@ -139,6 +182,21 @@ handleEvent(client, data) {
139182

140183
> info **Hint** The `@CacheTTL()` decorator may be used with or without a corresponding `@CacheKey()` decorator.
141184

185+
#### Adjust tracking
186+
187+
By default, Nest uses the request URL (in an HTTP app) or cache key (in websockets and microservices apps, set through the `@CacheKey()` decorator) to associate cache records with your endpoints. Nevertheless, sometimes you might want to set up tracking based on different factors, for example, using HTTP headers (e.g. `Authorization` to properly identify `profile` endpoints).
188+
189+
In order to accomplish that, create a subclass of `CacheInterceptor` and override the `trackBy()` method.
190+
191+
```typescript
192+
@Injectable()
193+
class HttpCacheInterceptor extends CacheInterceptor {
194+
trackBy(context: ExecutionContext): string | undefined {
195+
return 'key';
196+
}
197+
}
198+
```
199+
142200
#### Different stores
143201
144202
This service takes advantage of [cache-manager](https://github.com/BryanDonovan/node-cache-manager) under the hood. The `cache-manager` package supports a wide-range of useful stores, for example, [Redis](https://github.com/dabroek/node-cache-manager-redis-store) store. A full list of supported stores is available [here](https://github.com/BryanDonovan/node-cache-manager#store-engines). To set up the Redis store, simply pass the package together with corresponding options to the `register()` method.
@@ -161,21 +219,6 @@ import { AppController } from './app.controller';
161219
export class ApplicationModule {}
162220
```
163221
164-
#### Adjust tracking
165-
166-
By default, Nest uses the request URL (in an HTTP app) or cache key (in websockets and microservices apps, set through the `@CacheKey()` decorator) to associate cache records with your endpoints. Nevertheless, sometimes you might want to set up tracking based on different factors, for example, using HTTP headers (e.g. `Authorization` to properly identify `profile` endpoints).
167-
168-
In order to accomplish that, create a subclass of `CacheInterceptor` and override the `trackBy()` method.
169-
170-
```typescript
171-
@Injectable()
172-
class HttpCacheInterceptor extends CacheInterceptor {
173-
trackBy(context: ExecutionContext): string | undefined {
174-
return 'key';
175-
}
176-
}
177-
```
178-
179222
#### Async configuration
180223
181224
You may want to asynchronously pass in module options instead of passing them statically at compile time. In this case, use the `registerAsync()` method, which provides several ways to deal with async configuration.
@@ -196,7 +239,7 @@ Our factory behaves like all other asynchronous module factories (it can be `asy
196239
CacheModule.registerAsync({
197240
imports: [ConfigModule],
198241
useFactory: async (configService: ConfigService) => ({
199-
ttl: configService.getString('CACHE_TTL'),
242+
ttl: configService.get('CACHE_TTL'),
200243
}),
201244
inject: [ConfigService],
202245
});

0 commit comments

Comments
 (0)