@mshick/dyno 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +54 -0
- package/dist/client.d.ts +4 -0
- package/dist/client.js +31 -0
- package/dist/constants.d.ts +1 -0
- package/dist/constants.js +1 -0
- package/dist/dyno.d.ts +161 -0
- package/dist/dyno.js +289 -0
- package/dist/error.d.ts +3 -0
- package/dist/error.js +5 -0
- package/dist/index.d.ts +12 -0
- package/dist/index.js +4 -0
- package/dist/paginated.d.ts +3 -0
- package/dist/paginated.js +19 -0
- package/dist/requests/requests.d.ts +16 -0
- package/dist/requests/requests.js +225 -0
- package/dist/requests/send-all.d.ts +43 -0
- package/dist/requests/send-all.js +163 -0
- package/dist/requests/send-completely.d.ts +48 -0
- package/dist/requests/send-completely.js +231 -0
- package/dist/requests/types.d.ts +32 -0
- package/dist/requests/types.js +1 -0
- package/dist/responses.d.ts +11 -0
- package/dist/responses.js +47 -0
- package/dist/stream.d.ts +44 -0
- package/dist/stream.js +205 -0
- package/dist/streams/dyno-readable-stream.d.ts +24 -0
- package/dist/streams/dyno-readable-stream.js +41 -0
- package/dist/streams/dyno-writable-stream.d.ts +18 -0
- package/dist/streams/dyno-writable-stream.js +29 -0
- package/dist/streams/parallel-writable.d.ts +8 -0
- package/dist/streams/parallel-writable.js +52 -0
- package/dist/table.d.ts +28 -0
- package/dist/table.js +161 -0
- package/dist/types.d.ts +42 -0
- package/dist/types.js +1 -0
- package/dist/util.d.ts +32 -0
- package/dist/util.js +272 -0
- package/package.json +82 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Michael Shick
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
# @mshick/dyno
|
|
2
|
+
|
|
3
|
+
A simple DynamoDB client, inspired by [dyno](https://github.com/mapbox/dyno).
|
|
4
|
+
|
|
5
|
+
## Install
|
|
6
|
+
|
|
7
|
+
```sh
|
|
8
|
+
pnpm add @mshick/dyno
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## Example
|
|
12
|
+
|
|
13
|
+
```typescript
|
|
14
|
+
import { Dyno } from '@mshick/dyno';
|
|
15
|
+
|
|
16
|
+
const table = new Dyno({ table: 'my-table', region: 'us-east-1' });
|
|
17
|
+
|
|
18
|
+
await table.ensureTable({
|
|
19
|
+
AttributeDefinitions: [{ AttributeName: 'id', AttributeType: 'S' }],
|
|
20
|
+
KeySchema: [{ AttributeName: 'id', KeyType: 'HASH' }],
|
|
21
|
+
});
|
|
22
|
+
|
|
23
|
+
await table.batchPutAll([{ id: 'a' }, { id: 'b' }]).sendAll();
|
|
24
|
+
|
|
25
|
+
const { Items } = await table.scan({ Pages: Infinity });
|
|
26
|
+
console.log(Items); // [{id: 'a'}, {id: 'b'}]
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
For supported methods and more examples, see the [`Dyno` tests](./src/__tests__/dyno.test.ts).
|
|
30
|
+
|
|
31
|
+
## Development
|
|
32
|
+
|
|
33
|
+
This project uses [pnpm](https://pnpm.io). Tests use a local DynamoDB via
|
|
34
|
+
Docker (`docker-compose.yml`), so make sure Docker is running.
|
|
35
|
+
|
|
36
|
+
```sh
|
|
37
|
+
pnpm install
|
|
38
|
+
pnpm test # spins up DynamoDB, runs vitest
|
|
39
|
+
pnpm check # tsc --noEmit
|
|
40
|
+
pnpm lint # biome check
|
|
41
|
+
pnpm build # emits dist/
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
## Release
|
|
45
|
+
|
|
46
|
+
Releases are driven by [release-please](https://github.com/googleapis/release-please)
|
|
47
|
+
on the `main` branch. PR titles and the first commit on a branch must follow
|
|
48
|
+
[Conventional Commits](https://www.conventionalcommits.org/) (e.g.
|
|
49
|
+
`feat: add new method`, `fix: handle empty batch`). Subsequent commits on a
|
|
50
|
+
branch can use plain descriptive messages.
|
|
51
|
+
|
|
52
|
+
## License
|
|
53
|
+
|
|
54
|
+
[MIT](./LICENSE)
|
package/dist/client.d.ts
ADDED
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { DynamoDBClientConfig } from '@aws-sdk/client-dynamodb';
|
|
2
|
+
import type { TranslateConfig } from '@aws-sdk/lib-dynamodb';
|
|
3
|
+
export declare function getClientConfig(config: DynamoDBClientConfig): DynamoDBClientConfig;
|
|
4
|
+
export declare function getClientTranslateConfig(config?: TranslateConfig): TranslateConfig;
|
package/dist/client.js
ADDED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import https from 'node:https';
|
|
2
|
+
import { NodeHttpHandler } from '@smithy/node-http-handler';
|
|
3
|
+
import { REGION } from "./constants.js";
|
|
4
|
+
export function getClientConfig(config) {
|
|
5
|
+
return {
|
|
6
|
+
maxAttempts: 6,
|
|
7
|
+
requestHandler: new NodeHttpHandler({
|
|
8
|
+
// Disabled due to timeouts with SSG — effectively no connectionTimeout
|
|
9
|
+
// connectionTimeout: 1000,
|
|
10
|
+
requestTimeout: 5000,
|
|
11
|
+
httpsAgent: new https.Agent({
|
|
12
|
+
// Set this explicitly, since we provide an agent, we can't rely on defaults
|
|
13
|
+
keepAlive: true,
|
|
14
|
+
maxSockets: 400, // default is 50
|
|
15
|
+
}),
|
|
16
|
+
}),
|
|
17
|
+
region: REGION,
|
|
18
|
+
...config,
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
export function getClientTranslateConfig(config) {
|
|
22
|
+
return {
|
|
23
|
+
marshallOptions: {
|
|
24
|
+
removeUndefinedValues: true,
|
|
25
|
+
...config?.marshallOptions,
|
|
26
|
+
},
|
|
27
|
+
unmarshallOptions: {
|
|
28
|
+
...config?.unmarshallOptions,
|
|
29
|
+
},
|
|
30
|
+
};
|
|
31
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const REGION = "us-east-1";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const REGION = 'us-east-1';
|
package/dist/dyno.d.ts
ADDED
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
import { type CreateTableCommandInput, type DeleteTableCommandInput, type DescribeTableCommandInput, DynamoDB, type DynamoDBClientConfig, type ListTablesCommandInput } from '@aws-sdk/client-dynamodb';
|
|
2
|
+
import { type BatchGetCommandInput, type BatchWriteCommandInput, type DeleteCommandInput, DynamoDBDocument, type GetCommandInput, type PutCommandInput, type TranslateConfig, type UpdateCommandInput } from '@aws-sdk/lib-dynamodb';
|
|
3
|
+
import type { HttpHandlerOptions } from '@smithy/types';
|
|
4
|
+
import type { SendAllOptions } from './requests/send-all.ts';
|
|
5
|
+
import type { SendCompletelyOptions } from './requests/send-completely.ts';
|
|
6
|
+
import { type ParseResponseOptions } from './responses.ts';
|
|
7
|
+
import { type PutStreamInput, type PutStreamOptions, type QueryInput, type QueryOutput, type ReadStreamOptions, type ScanInput, type ScanOutput } from './stream.ts';
|
|
8
|
+
import { type WaitForConnectionOptions, type WaitForIndexOperation, type WaitForIndexParams, type WaitForTableOperation, type WaitForTableParams } from './table.ts';
|
|
9
|
+
import type { EnsureTableInput, NativeAttributeMap, OptionalTableName } from './types.ts';
|
|
10
|
+
export type DynoConfig<T extends string | undefined = string> = DynamoDBClientConfig & {
|
|
11
|
+
table: T;
|
|
12
|
+
} & SendCompletelyOptions & SendAllOptions & ParseResponseOptions & {
|
|
13
|
+
translateConfig?: TranslateConfig;
|
|
14
|
+
};
|
|
15
|
+
/**
|
|
16
|
+
* Extends an interface matching the `dynoExtensions` in `dyno`. Native methods
|
|
17
|
+
* can be
|
|
18
|
+
*/
|
|
19
|
+
export declare class Dyno<TableName extends string | undefined = undefined> {
|
|
20
|
+
/**
|
|
21
|
+
* Create a DynamoDB client with defaults
|
|
22
|
+
*/
|
|
23
|
+
static createClient(config: DynamoDBClientConfig): DynamoDB;
|
|
24
|
+
/**
|
|
25
|
+
* Create a DynamoDBDocument client with defaults
|
|
26
|
+
*/
|
|
27
|
+
static createDocumentClient(client: DynamoDB, translateConfig?: TranslateConfig): DynamoDBDocument;
|
|
28
|
+
/**
|
|
29
|
+
* Create a Dynamo instance from a client
|
|
30
|
+
*
|
|
31
|
+
* Note: Not in Dyno
|
|
32
|
+
*/
|
|
33
|
+
static from(client: DynamoDB): Dyno<undefined>;
|
|
34
|
+
readonly config: DynoConfig<TableName>;
|
|
35
|
+
readonly tableName: TableName;
|
|
36
|
+
private readonly _client;
|
|
37
|
+
private readonly _docClient;
|
|
38
|
+
constructor(config: DynoConfig<TableName>, client?: DynamoDB);
|
|
39
|
+
/**
|
|
40
|
+
* Destroy the DynamoDB client
|
|
41
|
+
*
|
|
42
|
+
* Note: Not in Dyno
|
|
43
|
+
*/
|
|
44
|
+
destroy(): void;
|
|
45
|
+
/**
|
|
46
|
+
* Get a sub-client, scoped to a single table. Similar to the behavior of the Dyno class constructor.
|
|
47
|
+
*
|
|
48
|
+
* Note: Not in Dyno
|
|
49
|
+
*/
|
|
50
|
+
table(tableName: string): Dyno<string>;
|
|
51
|
+
ensureTable(params?: OptionalTableName<EnsureTableInput, TableName>): Promise<import("./table.ts").EnsureTableOutput>;
|
|
52
|
+
waitForConnection(options?: WaitForConnectionOptions): Promise<void>;
|
|
53
|
+
killConnection(): void;
|
|
54
|
+
waitForIndex(operation: WaitForIndexOperation, params: OptionalTableName<WaitForIndexParams, TableName>): Promise<void>;
|
|
55
|
+
waitForTable(operation: WaitForTableOperation, params?: OptionalTableName<WaitForTableParams, TableName>): Promise<void>;
|
|
56
|
+
/**
|
|
57
|
+
* List the tables available in a given region. Passthrough to [DynamoDB.listTables](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#listTables-property).
|
|
58
|
+
*/
|
|
59
|
+
listTables(params?: ListTablesCommandInput): Promise<import("@aws-sdk/client-dynamodb").ListTablesCommandOutput>;
|
|
60
|
+
/**
|
|
61
|
+
* Get table information. Passthrough to [DynamoDB.describeTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#describTable-property).
|
|
62
|
+
*/
|
|
63
|
+
describeTable(params?: OptionalTableName<DescribeTableCommandInput, TableName>): Promise<{
|
|
64
|
+
Table: import("@aws-sdk/client-dynamodb").TableDescription;
|
|
65
|
+
}>;
|
|
66
|
+
/**
|
|
67
|
+
* Perform a batch of get operations. Passthrough to [DocumentClient.batchGet](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#batchGet-property).
|
|
68
|
+
*/
|
|
69
|
+
batchGetItem(params: TableName extends string ? NonNullable<BatchGetCommandInput['RequestItems']>[string] : BatchGetCommandInput, options?: HttpHandlerOptions): Promise<import("@aws-sdk/lib-dynamodb").BatchGetCommandOutput>;
|
|
70
|
+
/**
|
|
71
|
+
* Perform a batch of write operations. Passthrough to [DocumentClient.batchWrite](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#batchWrite-property).
|
|
72
|
+
*/
|
|
73
|
+
batchWriteItem(params: TableName extends string ? NonNullable<BatchWriteCommandInput['RequestItems']>[string] : BatchWriteCommandInput, options?: HttpHandlerOptions): Promise<import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
74
|
+
/**
|
|
75
|
+
* Delete a single record. Passthrough to [DocumentClient.delete](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#delete-property).
|
|
76
|
+
*/
|
|
77
|
+
deleteItem(params: OptionalTableName<DeleteCommandInput, TableName>): Promise<import("@aws-sdk/lib-dynamodb").DeleteCommandOutput>;
|
|
78
|
+
/**
|
|
79
|
+
* Get a single record. Passthrough to [DocumentClient.get](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#get-property).
|
|
80
|
+
*/
|
|
81
|
+
getItem(params: OptionalTableName<GetCommandInput, TableName>): Promise<import("@aws-sdk/lib-dynamodb").GetCommandOutput>;
|
|
82
|
+
/**
|
|
83
|
+
* Put a single record. Passthrough to [DocumentClient.put](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#put-property).
|
|
84
|
+
*/
|
|
85
|
+
putItem(params: OptionalTableName<PutCommandInput, TableName>): Promise<import("@aws-sdk/lib-dynamodb").PutCommandOutput>;
|
|
86
|
+
/**
|
|
87
|
+
* Update a single record. Passthrough to [DocumentClient.update](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#update-property).
|
|
88
|
+
*/
|
|
89
|
+
updateItem(params: OptionalTableName<UpdateCommandInput, TableName>): Promise<import("@aws-sdk/lib-dynamodb").UpdateCommandOutput>;
|
|
90
|
+
/**
|
|
91
|
+
* Break a large batch of get operations into a set of requests that can be
|
|
92
|
+
* sent individually or concurrently.
|
|
93
|
+
*/
|
|
94
|
+
batchGetItemRequests(params: TableName extends string ? NonNullable<BatchGetCommandInput['RequestItems']>[string] : BatchGetCommandInput, options?: HttpHandlerOptions & SendAllOptions): import("./requests/send-all.ts").SendAllBatch<BatchGetCommandInput, import("@aws-sdk/lib-dynamodb").BatchGetCommandOutput>;
|
|
95
|
+
/**
|
|
96
|
+
* Break a large batch of write operations into a set of requests that can be
|
|
97
|
+
* sent individually or concurrently.
|
|
98
|
+
*/
|
|
99
|
+
batchWriteItemRequests(params: TableName extends string ? NonNullable<BatchWriteCommandInput['RequestItems']>[string] : BatchWriteCommandInput, options?: HttpHandlerOptions & SendAllOptions): import("./requests/send-all.ts").SendAllBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
100
|
+
/**
|
|
101
|
+
* Break a large batch of get operations into a set of requests that are intended
|
|
102
|
+
* to be sent concurrently.
|
|
103
|
+
*/
|
|
104
|
+
batchGetAll(params: TableName extends string ? NonNullable<BatchGetCommandInput['RequestItems']>[string] : BatchGetCommandInput, options?: HttpHandlerOptions & SendCompletelyOptions): import("./requests/send-completely.ts").SendCompletelyBatch<BatchGetCommandInput, import("@aws-sdk/lib-dynamodb").BatchGetCommandOutput>;
|
|
105
|
+
/**
|
|
106
|
+
* Break a large batch of write operations into a set of requests that are intended
|
|
107
|
+
* to be sent concurrently.
|
|
108
|
+
*/
|
|
109
|
+
batchWriteAll(params: TableName extends string ? NonNullable<BatchWriteCommandInput['RequestItems']>[string] : BatchWriteCommandInput, options?: HttpHandlerOptions & SendCompletelyOptions): import("./requests/send-completely.ts").SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
110
|
+
/**
|
|
111
|
+
* Sugar on batchWriteAll, only for table clients
|
|
112
|
+
*/
|
|
113
|
+
batchPutAll(items: TableName extends string ? NativeAttributeMap[] : never, options?: HttpHandlerOptions & SendCompletelyOptions): import("./requests/send-completely.ts").SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
114
|
+
/**
|
|
115
|
+
* Sugar on batchWriteAll, only for table clients
|
|
116
|
+
*/
|
|
117
|
+
batchDeleteAll(items: TableName extends string ? NativeAttributeMap[] : never, options?: HttpHandlerOptions & SendCompletelyOptions): import("./requests/send-completely.ts").SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
118
|
+
/**
|
|
119
|
+
* Create a table. Passthrough to [DynamoDB.createTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#createTable-property),
|
|
120
|
+
* except the function polls DynamoDB until the table is ready to accept
|
|
121
|
+
* reads and writes, at which point the callback function is called.
|
|
122
|
+
*/
|
|
123
|
+
createTable(params: OptionalTableName<CreateTableCommandInput, TableName>): Promise<{
|
|
124
|
+
TableDescription: import("@aws-sdk/client-dynamodb").TableDescription;
|
|
125
|
+
}>;
|
|
126
|
+
/**
|
|
127
|
+
* Delete a table. Passthrough to [DynamoDB.deleteTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#deleteTable-property),
|
|
128
|
+
* except the function polls DynamoDB until the table is ready to accept
|
|
129
|
+
* reads and writes, at which point the callback function is called.
|
|
130
|
+
*/
|
|
131
|
+
deleteTable(params?: OptionalTableName<DeleteTableCommandInput, TableName>): Promise<void>;
|
|
132
|
+
/**
|
|
133
|
+
* Provide the results of a query as a [Readable Stream](https://nodejs.org/api/stream.html#stream_class_stream_readable).
|
|
134
|
+
* This function will paginate through query responses, making HTTP requests
|
|
135
|
+
* as the caller reads from the stream.
|
|
136
|
+
*/
|
|
137
|
+
queryStream(params: OptionalTableName<QueryInput, TableName>, options?: ReadStreamOptions): import("./index.ts").DynoReadableStream;
|
|
138
|
+
/**
|
|
139
|
+
* Provide the results of a scan as a [Readable Stream](https://nodejs.org/api/stream.html#stream_class_stream_readable).
|
|
140
|
+
* This function will paginate through query responses, making HTTP requests
|
|
141
|
+
* as the caller reads from the stream.
|
|
142
|
+
*/
|
|
143
|
+
scanStream(params?: OptionalTableName<ScanInput, TableName>, options?: ReadStreamOptions): import("./index.ts").DynoReadableStream;
|
|
144
|
+
/**
|
|
145
|
+
* Creates a [Writable stream](https://nodejs.org/api/stream.html#stream_class_stream_writable).
|
|
146
|
+
* Writing individual records to the stream will aggregate them into sets of
|
|
147
|
+
* 25 items and submit them as `BatchWriteItem` requests.
|
|
148
|
+
*/
|
|
149
|
+
putStream(params?: OptionalTableName<PutStreamInput, TableName>, options?: PutStreamOptions): import("./index.ts").DynoWritableStream;
|
|
150
|
+
/**
|
|
151
|
+
* Query a table or secondary index. Passthrough to [DocumentClient.query](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#query-property).
|
|
152
|
+
*/
|
|
153
|
+
query(params: OptionalTableName<QueryInput, TableName>, options?: ReadStreamOptions): Promise<QueryOutput>;
|
|
154
|
+
/**
|
|
155
|
+
* Scan a table or secondary index. Passthrough to [DocumentClient.scan](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#scan-property).
|
|
156
|
+
*/
|
|
157
|
+
scan(params?: OptionalTableName<ScanInput, TableName>, options?: ReadStreamOptions): Promise<ScanOutput>;
|
|
158
|
+
private paramsWithTableName;
|
|
159
|
+
private batchParams;
|
|
160
|
+
private batchOptions;
|
|
161
|
+
}
|
package/dist/dyno.js
ADDED
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
import { DynamoDB, } from '@aws-sdk/client-dynamodb';
|
|
2
|
+
import { DynamoDBDocument, } from '@aws-sdk/lib-dynamodb';
|
|
3
|
+
import { getClientConfig, getClientTranslateConfig } from "./client.js";
|
|
4
|
+
import { TableNameError } from "./error.js";
|
|
5
|
+
import { readPaginatedStream } from "./paginated.js";
|
|
6
|
+
import { batchDeleteAll, batchGetAll, batchGetItemRequests, batchPutAll, batchWriteAll, batchWriteItemRequests, } from "./requests/requests.js";
|
|
7
|
+
import { parseResponse } from "./responses.js";
|
|
8
|
+
import { createPutStream, createReadStream, } from "./stream.js";
|
|
9
|
+
import { createTable, deleteTable, ensureTable, killConnection, waitForConnection, waitForIndex, waitForTable, } from "./table.js";
|
|
10
|
+
/**
|
|
11
|
+
* Extends an interface matching the `dynoExtensions` in `dyno`. Native methods
|
|
12
|
+
* can be
|
|
13
|
+
*/
|
|
14
|
+
export class Dyno {
|
|
15
|
+
/**
|
|
16
|
+
* Create a DynamoDB client with defaults
|
|
17
|
+
*/
|
|
18
|
+
static createClient(config) {
|
|
19
|
+
return new DynamoDB(getClientConfig(config));
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Create a DynamoDBDocument client with defaults
|
|
23
|
+
*/
|
|
24
|
+
static createDocumentClient(client, translateConfig) {
|
|
25
|
+
return DynamoDBDocument.from(client, getClientTranslateConfig(translateConfig));
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Create a Dynamo instance from a client
|
|
29
|
+
*
|
|
30
|
+
* Note: Not in Dyno
|
|
31
|
+
*/
|
|
32
|
+
static from(client) {
|
|
33
|
+
return new Dyno({ table: undefined }, client);
|
|
34
|
+
}
|
|
35
|
+
config;
|
|
36
|
+
tableName;
|
|
37
|
+
_client;
|
|
38
|
+
_docClient;
|
|
39
|
+
constructor(config, client) {
|
|
40
|
+
let { table, maxRetries, concurrency, translateConfig, ...clientConfig } = config;
|
|
41
|
+
if (client) {
|
|
42
|
+
this._client = client;
|
|
43
|
+
}
|
|
44
|
+
else {
|
|
45
|
+
clientConfig = getClientConfig(clientConfig);
|
|
46
|
+
this._client = Dyno.createClient(clientConfig);
|
|
47
|
+
}
|
|
48
|
+
translateConfig = getClientTranslateConfig(translateConfig);
|
|
49
|
+
this._docClient = DynamoDBDocument.from(this._client, translateConfig);
|
|
50
|
+
this.tableName = table;
|
|
51
|
+
this.config = {
|
|
52
|
+
table,
|
|
53
|
+
maxRetries,
|
|
54
|
+
concurrency,
|
|
55
|
+
translateConfig,
|
|
56
|
+
...clientConfig,
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Destroy the DynamoDB client
|
|
61
|
+
*
|
|
62
|
+
* Note: Not in Dyno
|
|
63
|
+
*/
|
|
64
|
+
destroy() {
|
|
65
|
+
this._client.destroy();
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Get a sub-client, scoped to a single table. Similar to the behavior of the Dyno class constructor.
|
|
69
|
+
*
|
|
70
|
+
* Note: Not in Dyno
|
|
71
|
+
*/
|
|
72
|
+
table(tableName) {
|
|
73
|
+
return new Dyno({ ...this.config, table: tableName }, this._client);
|
|
74
|
+
}
|
|
75
|
+
async ensureTable(params) {
|
|
76
|
+
return ensureTable(this._client, this.paramsWithTableName(params));
|
|
77
|
+
}
|
|
78
|
+
async waitForConnection(options) {
|
|
79
|
+
return waitForConnection(this._client, options);
|
|
80
|
+
}
|
|
81
|
+
killConnection() {
|
|
82
|
+
killConnection(this._client);
|
|
83
|
+
}
|
|
84
|
+
async waitForIndex(operation, params) {
|
|
85
|
+
return waitForIndex(this._client, this.paramsWithTableName(params), operation);
|
|
86
|
+
}
|
|
87
|
+
async waitForTable(operation, params) {
|
|
88
|
+
return waitForTable(this._client, this.paramsWithTableName(params), operation);
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* List the tables available in a given region. Passthrough to [DynamoDB.listTables](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#listTables-property).
|
|
92
|
+
*/
|
|
93
|
+
async listTables(params) {
|
|
94
|
+
return this._client.listTables(params ?? {});
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Get table information. Passthrough to [DynamoDB.describeTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#describTable-property).
|
|
98
|
+
*/
|
|
99
|
+
async describeTable(params) {
|
|
100
|
+
const { Table } = await this._client.describeTable(this.paramsWithTableName(params));
|
|
101
|
+
if (!Table) {
|
|
102
|
+
throw new Error('Missing Table in response');
|
|
103
|
+
}
|
|
104
|
+
return { Table };
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Perform a batch of get operations. Passthrough to [DocumentClient.batchGet](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#batchGet-property).
|
|
108
|
+
*/
|
|
109
|
+
async batchGetItem(params, options) {
|
|
110
|
+
return parseResponse(await this._docClient.batchGet(this.batchParams(params), options), this.config);
|
|
111
|
+
}
|
|
112
|
+
/**
|
|
113
|
+
* Perform a batch of write operations. Passthrough to [DocumentClient.batchWrite](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#batchWrite-property).
|
|
114
|
+
*/
|
|
115
|
+
async batchWriteItem(params, options) {
|
|
116
|
+
return this._docClient.batchWrite(this.batchParams(params), options);
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Delete a single record. Passthrough to [DocumentClient.delete](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#delete-property).
|
|
120
|
+
*/
|
|
121
|
+
async deleteItem(params) {
|
|
122
|
+
return this._docClient.delete(this.paramsWithTableName(params));
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Get a single record. Passthrough to [DocumentClient.get](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#get-property).
|
|
126
|
+
*/
|
|
127
|
+
async getItem(params) {
|
|
128
|
+
return parseResponse(await this._docClient.get(this.paramsWithTableName(params)), this.config);
|
|
129
|
+
}
|
|
130
|
+
/**
|
|
131
|
+
* Put a single record. Passthrough to [DocumentClient.put](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#put-property).
|
|
132
|
+
*/
|
|
133
|
+
async putItem(params) {
|
|
134
|
+
return this._docClient.put(this.paramsWithTableName(params));
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* Update a single record. Passthrough to [DocumentClient.update](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#update-property).
|
|
138
|
+
*/
|
|
139
|
+
async updateItem(params) {
|
|
140
|
+
return this._docClient.update(this.paramsWithTableName(params));
|
|
141
|
+
}
|
|
142
|
+
/**
|
|
143
|
+
* Break a large batch of get operations into a set of requests that can be
|
|
144
|
+
* sent individually or concurrently.
|
|
145
|
+
*/
|
|
146
|
+
batchGetItemRequests(params, options) {
|
|
147
|
+
return batchGetItemRequests(this._docClient, this.batchParams(params), this.batchOptions(options));
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Break a large batch of write operations into a set of requests that can be
|
|
151
|
+
* sent individually or concurrently.
|
|
152
|
+
*/
|
|
153
|
+
batchWriteItemRequests(params, options) {
|
|
154
|
+
return batchWriteItemRequests(this._docClient, this.batchParams(params), this.batchOptions(options));
|
|
155
|
+
}
|
|
156
|
+
/**
|
|
157
|
+
* Break a large batch of get operations into a set of requests that are intended
|
|
158
|
+
* to be sent concurrently.
|
|
159
|
+
*/
|
|
160
|
+
batchGetAll(params, options) {
|
|
161
|
+
return batchGetAll(this._docClient, this.batchParams(params), this.batchOptions(options));
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Break a large batch of write operations into a set of requests that are intended
|
|
165
|
+
* to be sent concurrently.
|
|
166
|
+
*/
|
|
167
|
+
batchWriteAll(params, options) {
|
|
168
|
+
return batchWriteAll(this._docClient, this.batchParams(params), this.batchOptions(options));
|
|
169
|
+
}
|
|
170
|
+
/**
|
|
171
|
+
* Sugar on batchWriteAll, only for table clients
|
|
172
|
+
*/
|
|
173
|
+
batchPutAll(items, options) {
|
|
174
|
+
if (!this.tableName) {
|
|
175
|
+
throw new TableNameError();
|
|
176
|
+
}
|
|
177
|
+
return batchPutAll(this._docClient, this.tableName, items, this.batchOptions(options));
|
|
178
|
+
}
|
|
179
|
+
/**
|
|
180
|
+
* Sugar on batchWriteAll, only for table clients
|
|
181
|
+
*/
|
|
182
|
+
batchDeleteAll(items, options) {
|
|
183
|
+
if (!this.tableName) {
|
|
184
|
+
throw new TableNameError();
|
|
185
|
+
}
|
|
186
|
+
return batchDeleteAll(this._docClient, this.tableName, items, this.batchOptions(options));
|
|
187
|
+
}
|
|
188
|
+
/**
|
|
189
|
+
* Create a table. Passthrough to [DynamoDB.createTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#createTable-property),
|
|
190
|
+
* except the function polls DynamoDB until the table is ready to accept
|
|
191
|
+
* reads and writes, at which point the callback function is called.
|
|
192
|
+
*/
|
|
193
|
+
async createTable(params) {
|
|
194
|
+
return createTable(this._client, this.paramsWithTableName(params));
|
|
195
|
+
}
|
|
196
|
+
/**
|
|
197
|
+
* Delete a table. Passthrough to [DynamoDB.deleteTable](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB.html#deleteTable-property),
|
|
198
|
+
* except the function polls DynamoDB until the table is ready to accept
|
|
199
|
+
* reads and writes, at which point the callback function is called.
|
|
200
|
+
*/
|
|
201
|
+
async deleteTable(params) {
|
|
202
|
+
return deleteTable(this._client, this.paramsWithTableName(params));
|
|
203
|
+
}
|
|
204
|
+
/**
|
|
205
|
+
* Provide the results of a query as a [Readable Stream](https://nodejs.org/api/stream.html#stream_class_stream_readable).
|
|
206
|
+
* This function will paginate through query responses, making HTTP requests
|
|
207
|
+
* as the caller reads from the stream.
|
|
208
|
+
*/
|
|
209
|
+
queryStream(params, options) {
|
|
210
|
+
return createReadStream(this._docClient, this.paramsWithTableName(params), {
|
|
211
|
+
...options,
|
|
212
|
+
mode: 'query',
|
|
213
|
+
});
|
|
214
|
+
}
|
|
215
|
+
/**
|
|
216
|
+
* Provide the results of a scan as a [Readable Stream](https://nodejs.org/api/stream.html#stream_class_stream_readable).
|
|
217
|
+
* This function will paginate through query responses, making HTTP requests
|
|
218
|
+
* as the caller reads from the stream.
|
|
219
|
+
*/
|
|
220
|
+
scanStream(params, options) {
|
|
221
|
+
return createReadStream(this._docClient, this.paramsWithTableName(params), {
|
|
222
|
+
...options,
|
|
223
|
+
mode: 'scan',
|
|
224
|
+
});
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* Creates a [Writable stream](https://nodejs.org/api/stream.html#stream_class_stream_writable).
|
|
228
|
+
* Writing individual records to the stream will aggregate them into sets of
|
|
229
|
+
* 25 items and submit them as `BatchWriteItem` requests.
|
|
230
|
+
*/
|
|
231
|
+
putStream(params, options) {
|
|
232
|
+
const { concurrency, maxRetries } = this.config;
|
|
233
|
+
return createPutStream(this._docClient, this.paramsWithTableName(params), {
|
|
234
|
+
concurrency,
|
|
235
|
+
maxRetries,
|
|
236
|
+
...options,
|
|
237
|
+
});
|
|
238
|
+
}
|
|
239
|
+
/**
|
|
240
|
+
* Query a table or secondary index. Passthrough to [DocumentClient.query](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#query-property).
|
|
241
|
+
*/
|
|
242
|
+
async query(params, options) {
|
|
243
|
+
if (!params?.Pages) {
|
|
244
|
+
return this._docClient.query(this.paramsWithTableName(params));
|
|
245
|
+
}
|
|
246
|
+
return readPaginatedStream(this.queryStream(params, options));
|
|
247
|
+
}
|
|
248
|
+
/**
|
|
249
|
+
* Scan a table or secondary index. Passthrough to [DocumentClient.scan](http://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/DynamoDB/DocumentClient.html#scan-property).
|
|
250
|
+
*/
|
|
251
|
+
async scan(params, options) {
|
|
252
|
+
if (!params?.Pages) {
|
|
253
|
+
return this._docClient.scan(this.paramsWithTableName(params));
|
|
254
|
+
}
|
|
255
|
+
return readPaginatedStream(this.scanStream(params, options));
|
|
256
|
+
}
|
|
257
|
+
paramsWithTableName(params) {
|
|
258
|
+
// Class-defined tableName takes precedence
|
|
259
|
+
const TableName = this.tableName ?? params?.TableName;
|
|
260
|
+
if (!TableName) {
|
|
261
|
+
throw new TableNameError();
|
|
262
|
+
}
|
|
263
|
+
return { TableName, ...params };
|
|
264
|
+
}
|
|
265
|
+
batchParams(requestOrItems) {
|
|
266
|
+
let params;
|
|
267
|
+
if ('RequestItems' in requestOrItems) {
|
|
268
|
+
params = requestOrItems;
|
|
269
|
+
}
|
|
270
|
+
else {
|
|
271
|
+
if (!this.tableName) {
|
|
272
|
+
throw new TableNameError();
|
|
273
|
+
}
|
|
274
|
+
params = {
|
|
275
|
+
RequestItems: { [this.tableName]: requestOrItems },
|
|
276
|
+
};
|
|
277
|
+
}
|
|
278
|
+
return params;
|
|
279
|
+
}
|
|
280
|
+
batchOptions(options) {
|
|
281
|
+
const { concurrency, maxRetries, noBuffers } = this.config;
|
|
282
|
+
return {
|
|
283
|
+
concurrency,
|
|
284
|
+
maxRetries,
|
|
285
|
+
noBuffers,
|
|
286
|
+
...options,
|
|
287
|
+
};
|
|
288
|
+
}
|
|
289
|
+
}
|
package/dist/error.d.ts
ADDED
package/dist/error.js
ADDED
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export * from './client.ts';
|
|
2
|
+
export * from './dyno.ts';
|
|
3
|
+
export * from './error.ts';
|
|
4
|
+
export type * from './requests/requests.ts';
|
|
5
|
+
export type * from './requests/send-all.ts';
|
|
6
|
+
export type * from './requests/send-completely.ts';
|
|
7
|
+
export type * from './stream.ts';
|
|
8
|
+
export type * from './streams/dyno-readable-stream.ts';
|
|
9
|
+
export type * from './streams/dyno-writable-stream.ts';
|
|
10
|
+
export type * from './table.ts';
|
|
11
|
+
export type * from './types.ts';
|
|
12
|
+
export * from './util.ts';
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export async function readPaginatedStream(stream) {
|
|
2
|
+
return new Promise((resolve, reject) => {
|
|
3
|
+
const items = [];
|
|
4
|
+
stream
|
|
5
|
+
.on('error', reject)
|
|
6
|
+
.on('data', (item) => {
|
|
7
|
+
items.push(item);
|
|
8
|
+
})
|
|
9
|
+
.on('end', () => {
|
|
10
|
+
resolve({
|
|
11
|
+
Items: items,
|
|
12
|
+
Count: stream.Count,
|
|
13
|
+
ScannedCount: stream.ScannedCount,
|
|
14
|
+
LastEvaluatedKey: stream.LastEvaluatedKey,
|
|
15
|
+
ConsumedCapacity: stream.ConsumedCapacity,
|
|
16
|
+
});
|
|
17
|
+
});
|
|
18
|
+
});
|
|
19
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { BatchGetCommandInput, BatchWriteCommandInput, DynamoDBDocument } from '@aws-sdk/lib-dynamodb';
|
|
2
|
+
import type { HttpHandlerOptions } from '@smithy/types';
|
|
3
|
+
import { type ParseResponseOptions } from '../responses.ts';
|
|
4
|
+
import type { NativeAttributeMap } from '../types.ts';
|
|
5
|
+
import { SendAllBatch, type SendAllOptions } from './send-all.ts';
|
|
6
|
+
import { SendCompletelyBatch, type SendCompletelyOptions } from './send-completely.ts';
|
|
7
|
+
export type BatchWriteItemRequestsOptions = {
|
|
8
|
+
maxLength?: number;
|
|
9
|
+
maxSize?: number;
|
|
10
|
+
};
|
|
11
|
+
export declare function batchWriteItemRequests(client: DynamoDBDocument, params: BatchWriteCommandInput, options?: HttpHandlerOptions & BatchWriteItemRequestsOptions & SendAllOptions): SendAllBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
12
|
+
export declare function batchGetItemRequests(client: DynamoDBDocument, params: BatchGetCommandInput, options?: HttpHandlerOptions & SendAllOptions & ParseResponseOptions): SendAllBatch<BatchGetCommandInput, import("@aws-sdk/lib-dynamodb").BatchGetCommandOutput>;
|
|
13
|
+
export declare function batchWriteAll(client: DynamoDBDocument, params: BatchWriteCommandInput, options?: HttpHandlerOptions & SendCompletelyOptions): SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
14
|
+
export declare function batchPutAll(client: DynamoDBDocument, tableName: string, items: NativeAttributeMap[], options?: HttpHandlerOptions & SendCompletelyOptions): SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
15
|
+
export declare function batchDeleteAll(client: DynamoDBDocument, tableName: string, items: NativeAttributeMap[], options?: HttpHandlerOptions & SendCompletelyOptions): SendCompletelyBatch<BatchWriteCommandInput, import("@aws-sdk/lib-dynamodb").BatchWriteCommandOutput>;
|
|
16
|
+
export declare function batchGetAll(client: DynamoDBDocument, params: BatchGetCommandInput, options?: HttpHandlerOptions & SendCompletelyOptions & ParseResponseOptions): SendCompletelyBatch<BatchGetCommandInput, import("@aws-sdk/lib-dynamodb").BatchGetCommandOutput>;
|