You've already forked node-redis
mirror of
https://github.com/redis/node-redis.git
synced 2025-08-07 13:22:56 +03:00
Update README.MD (#2924)
* Update README.MD * docs: update programmability.md examples + add Programmability section to README and * fix imports according to the new v5 exports * more v5 docs updates --------- Co-authored-by: Nikolay Karadzhov <nkaradzhov89@gmail.com>
This commit is contained in:
@@ -23,7 +23,7 @@ By default, each type is mapped to the first option in the lists below. To chang
|
||||
- Double (`,`) => `number | string`
|
||||
- Simple String (`+`) => `string | Buffer`
|
||||
- Blob String (`$`) => `string | Buffer`
|
||||
- Verbatim String (`=`) => `string | Buffer | VerbatimString` (TODO: `VerbatimString` typedoc link)
|
||||
- Verbatim String (`=`) => `string | Buffer | VerbatimString`
|
||||
- Simple Error (`-`) => `ErrorReply`
|
||||
- Blob Error (`!`) => `ErrorReply`
|
||||
- Array (`*`) => `Array`
|
||||
|
@@ -25,16 +25,22 @@ FUNCTION LOAD "#!lua name=library\nredis.register_function{function_name='add',
|
||||
Load the prior redis function on the _redis server_ before running the example below.
|
||||
|
||||
```typescript
|
||||
import { createClient } from 'redis';
|
||||
import { CommandParser } from '@redis/client/lib/client/parser';
|
||||
import { NumberReply } from '@redis/client/lib/RESP/types';
|
||||
import { createClient, RedisArgument } from 'redis';
|
||||
|
||||
const client = createClient({
|
||||
functions: {
|
||||
library: {
|
||||
add: {
|
||||
NUMBER_OF_KEYS: 1,
|
||||
FIRST_KEY_INDEX: 1,
|
||||
transformArguments(key: string, toAdd: number): Array<string> {
|
||||
return [key, toAdd.toString()];
|
||||
parseCommand(
|
||||
parser: CommandParser,
|
||||
key: RedisArgument,
|
||||
toAdd: RedisArgument
|
||||
) {
|
||||
parser.pushKey(key)
|
||||
parser.push(toAdd)
|
||||
},
|
||||
transformReply: undefined as unknown as () => NumberReply
|
||||
}
|
||||
@@ -43,9 +49,8 @@ const client = createClient({
|
||||
});
|
||||
|
||||
await client.connect();
|
||||
|
||||
await client.set('key', '1');
|
||||
await client.library.add('key', 2); // 3
|
||||
await client.library.add('key', '2'); // 3
|
||||
```
|
||||
|
||||
## [Lua Scripts](https://redis.io/docs/manual/programmability/eval-intro/)
|
||||
@@ -53,7 +58,9 @@ await client.library.add('key', 2); // 3
|
||||
The following is an end-to-end example of the prior concept.
|
||||
|
||||
```typescript
|
||||
import { createClient, defineScript, NumberReply } from 'redis';
|
||||
import { CommandParser } from '@redis/client/lib/client/parser';
|
||||
import { NumberReply } from '@redis/client/lib/RESP/types';
|
||||
import { createClient, defineScript, RedisArgument } from 'redis';
|
||||
|
||||
const client = createClient({
|
||||
scripts: {
|
||||
@@ -61,8 +68,13 @@ const client = createClient({
|
||||
SCRIPT: 'return redis.call("GET", KEYS[1]) + ARGV[1];',
|
||||
NUMBER_OF_KEYS: 1,
|
||||
FIRST_KEY_INDEX: 1,
|
||||
transformArguments(key: string, toAdd: number): Array<string> {
|
||||
return [key, toAdd.toString()];
|
||||
parseCommand(
|
||||
parser: CommandParser,
|
||||
key: RedisArgument,
|
||||
toAdd: RedisArgument
|
||||
) {
|
||||
parser.pushKey(key)
|
||||
parser.push(toAdd)
|
||||
},
|
||||
transformReply: undefined as unknown as () => NumberReply
|
||||
})
|
||||
@@ -70,7 +82,6 @@ const client = createClient({
|
||||
});
|
||||
|
||||
await client.connect();
|
||||
|
||||
await client.set('key', '1');
|
||||
await client.add('key', 2); // 3
|
||||
await client.add('key', '2'); // 3
|
||||
```
|
||||
|
@@ -234,12 +234,12 @@ In v5, any unwritten commands (in the same pipeline) will be discarded.
|
||||
### Time Series
|
||||
|
||||
- `TS.ADD`: `boolean` -> `number` [^boolean-to-number]
|
||||
- `TS.[M][REV]RANGE`: `enum TimeSeriesBucketTimestamp` -> `const TIME_SERIES_BUCKET_TIMESTAMP` [^enum-to-constants], `enum TimeSeriesReducers` -> `const TIME_SERIES_REDUCERS` [^enum-to-constants], the `ALIGN` argument has been moved into `AGGREGRATION`
|
||||
- `TS.[M][REV]RANGE`: the `ALIGN` argument has been moved into `AGGREGATION`
|
||||
- `TS.SYNUPDATE`: `Array<string | Array<string>>` -> `Record<string, Array<string>>`
|
||||
- `TS.M[REV]RANGE[_WITHLABELS]`, `TS.MGET[_WITHLABELS]`: TODO
|
||||
|
||||
[^enum-to-constants]: TODO
|
||||
- `TimeSeriesDuplicatePolicies` -> `TIME_SERIES_DUPLICATE_POLICIES` [^enum-to-constants]
|
||||
- `TimeSeriesEncoding` -> `TIME_SERIES_ENCODING` [^enum-to-constants]
|
||||
- `TimeSeriesAggregationType` -> `TIME_SERIES_AGGREGATION_TYPE` [^enum-to-constants]
|
||||
- `TimeSeriesReducers` -> `TIME_SERIES_REDUCERS` [^enum-to-constants]
|
||||
- `TimeSeriesBucketTimestamp` -> `TIME_SERIES_BUCKET_TIMESTAMP` [^enum-to-constants]
|
||||
|
||||
[^map-keys]: To avoid unnecessary transformations and confusion, map keys will not be transformed to "js friendly" names (i.e. `number-of-keys` will not be renamed to `numberOfKeys`). See [here](https://github.com/redis/node-redis/discussions/2506).
|
||||
|
||||
[^future-proofing]: TODO
|
||||
|
65
docs/v5.md
65
docs/v5.md
@@ -1,30 +1,83 @@
|
||||
# RESP3 Support
|
||||
|
||||
TODO
|
||||
Node Redis v5 adds support for [RESP3](https://github.com/redis/redis-specifications/blob/master/protocol/RESP3.md), the new Redis serialization protocol. RESP3 offers richer data types and improved type handling compared to RESP2.
|
||||
|
||||
To use RESP3, specify it when creating your client:
|
||||
|
||||
```javascript
|
||||
import { createClient } from 'redis';
|
||||
|
||||
const client = createClient({
|
||||
RESP: 3
|
||||
});
|
||||
```
|
||||
|
||||
## Type Mapping
|
||||
|
||||
With RESP3, you can leverage the protocol's richer type system. You can customize how different Redis types are represented in JavaScript using type mapping:
|
||||
|
||||
```javascript
|
||||
// by default
|
||||
import { createClient, RESP_TYPES } from 'redis';
|
||||
|
||||
// By default
|
||||
await client.hGetAll('key'); // Record<string, string>
|
||||
|
||||
// Use Map instead of plain object
|
||||
await client.withTypeMapping({
|
||||
[TYPES.MAP]: Map
|
||||
[RESP_TYPES.MAP]: Map
|
||||
}).hGetAll('key'); // Map<string, string>
|
||||
|
||||
// Use both Map and Buffer
|
||||
await client.withTypeMapping({
|
||||
[TYPES.MAP]: Map,
|
||||
[TYPES.BLOB_STRING]: Buffer
|
||||
[RESP_TYPES.MAP]: Map,
|
||||
[RESP_TYPES.BLOB_STRING]: Buffer
|
||||
}).hGetAll('key'); // Map<string, Buffer>
|
||||
```
|
||||
|
||||
This replaces the previous approach of using `commandOptions({ returnBuffers: true })` in v4.
|
||||
|
||||
## PubSub in RESP3
|
||||
|
||||
RESP3 uses a different mechanism for handling Pub/Sub messages. Instead of modifying the `onReply` handler as in RESP2, RESP3 provides a dedicated `onPush` handler. When using RESP3, the client automatically uses this more efficient push notification system.
|
||||
|
||||
## Known Limitations
|
||||
|
||||
### Unstable Module Commands
|
||||
|
||||
Some Redis module commands have unstable RESP3 transformations. These commands will throw an error when used with RESP3 unless you explicitly opt in to using them by setting `unstableResp3: true` in your client configuration:
|
||||
|
||||
```javascript
|
||||
const client = createClient({
|
||||
RESP: 3,
|
||||
unstableResp3: true
|
||||
});
|
||||
```
|
||||
|
||||
The following commands have unstable RESP3 implementations:
|
||||
|
||||
1. **Stream Commands**:
|
||||
- `XREAD` and `XREADGROUP` - The response format differs between RESP2 and RESP3
|
||||
|
||||
2. **Search Commands (RediSearch)**:
|
||||
- `FT.AGGREGATE`
|
||||
- `FT.AGGREGATE_WITHCURSOR`
|
||||
- `FT.CURSOR_READ`
|
||||
- `FT.INFO`
|
||||
- `FT.PROFILE_AGGREGATE`
|
||||
- `FT.PROFILE_SEARCH`
|
||||
- `FT.SEARCH`
|
||||
- `FT.SEARCH_NOCONTENT`
|
||||
- `FT.SPELLCHECK`
|
||||
|
||||
3. **Time Series Commands**:
|
||||
- `TS.INFO`
|
||||
- `TS.INFO_DEBUG`
|
||||
|
||||
If you need to use these commands with RESP3, be aware that the response format might change in future versions.
|
||||
|
||||
# Sentinel Support
|
||||
|
||||
[TODO](./sentinel.md)
|
||||
[Sentinel](./sentinel.md)
|
||||
|
||||
# `multi.exec<'typed'>` / `multi.execTyped`
|
||||
|
||||
|
Reference in New Issue
Block a user