@forklaunch/infrastructure-s3 0.0.1
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/lib/eject/infrastructure/index.ts +230 -0
- package/lib/index.d.mts +157 -0
- package/lib/index.d.ts +157 -0
- package/lib/index.js +202 -0
- package/lib/index.js.map +1 -0
- package/lib/index.mjs +183 -0
- package/lib/index.mjs.map +1 -0
- package/package.json +59 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2024 forklaunch
|
|
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.
|
|
@@ -0,0 +1,230 @@
|
|
|
1
|
+
import {
|
|
2
|
+
DeleteObjectCommand,
|
|
3
|
+
DeleteObjectsCommand,
|
|
4
|
+
DeleteObjectsCommandInput,
|
|
5
|
+
GetObjectCommand,
|
|
6
|
+
PutObjectCommand,
|
|
7
|
+
PutObjectCommandInput,
|
|
8
|
+
S3Client
|
|
9
|
+
} from '@aws-sdk/client-s3';
|
|
10
|
+
import {
|
|
11
|
+
MetricsDefinition,
|
|
12
|
+
OpenTelemetryCollector,
|
|
13
|
+
TelemetryOptions
|
|
14
|
+
} from '@forklaunch/core/http';
|
|
15
|
+
import { ObjectStore } from '@forklaunch/core/objectstore';
|
|
16
|
+
import { Readable } from 'stream';
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Options for configuring the S3ObjectStore.
|
|
20
|
+
*
|
|
21
|
+
* @example
|
|
22
|
+
* const options: S3ObjectStoreOptions = {
|
|
23
|
+
* bucket: 'my-bucket',
|
|
24
|
+
* clientConfig: { region: 'us-west-2' }
|
|
25
|
+
* };
|
|
26
|
+
*/
|
|
27
|
+
interface S3ObjectStoreOptions {
|
|
28
|
+
/** The S3 bucket name. */
|
|
29
|
+
bucket: string;
|
|
30
|
+
/** Optional existing S3 client instance. */
|
|
31
|
+
client?: S3Client;
|
|
32
|
+
/** Optional configuration for creating a new S3 client. */
|
|
33
|
+
clientConfig?: ConstructorParameters<typeof S3Client>[0];
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* S3-backed implementation of the ObjectStore interface.
|
|
38
|
+
* Provides methods for storing, retrieving, streaming, and deleting objects in S3.
|
|
39
|
+
*
|
|
40
|
+
* @example
|
|
41
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
42
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
43
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
44
|
+
*/
|
|
45
|
+
export class S3ObjectStore implements ObjectStore<S3Client> {
|
|
46
|
+
private s3: S3Client;
|
|
47
|
+
private bucket: string;
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Creates a new S3ObjectStore instance.
|
|
51
|
+
* @param openTelemetryCollector - Collector for OpenTelemetry metrics.
|
|
52
|
+
* @param options - S3 configuration options.
|
|
53
|
+
* @param telemetryOptions - Telemetry configuration options.
|
|
54
|
+
*
|
|
55
|
+
* @example
|
|
56
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
57
|
+
*/
|
|
58
|
+
constructor(
|
|
59
|
+
private openTelemetryCollector: OpenTelemetryCollector<MetricsDefinition>,
|
|
60
|
+
options: S3ObjectStoreOptions,
|
|
61
|
+
private telemetryOptions: TelemetryOptions
|
|
62
|
+
) {
|
|
63
|
+
this.s3 = options.client || new S3Client(options.clientConfig || {});
|
|
64
|
+
this.bucket = options.bucket;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Stores an object in the S3 bucket.
|
|
69
|
+
* @template T - The type of the object being stored.
|
|
70
|
+
* @param object - The object to store. Must include a `key` property.
|
|
71
|
+
*
|
|
72
|
+
* @example
|
|
73
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
74
|
+
*/
|
|
75
|
+
async putObject<T>(object: T & { key: string }): Promise<void> {
|
|
76
|
+
const { key, ...rest } = object;
|
|
77
|
+
const params: PutObjectCommandInput = {
|
|
78
|
+
Bucket: this.bucket,
|
|
79
|
+
Key: key,
|
|
80
|
+
Body: JSON.stringify(rest),
|
|
81
|
+
ContentType: 'application/json'
|
|
82
|
+
};
|
|
83
|
+
await this.s3.send(new PutObjectCommand(params));
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* Stores multiple objects in the S3 bucket.
|
|
88
|
+
* @template T - The type of the objects being stored.
|
|
89
|
+
* @param objects - The objects to store. Each must include a `key` property.
|
|
90
|
+
*
|
|
91
|
+
* @example
|
|
92
|
+
* await store.putBatchObjects([
|
|
93
|
+
* { key: 'user-1', name: 'Alice' },
|
|
94
|
+
* { key: 'user-2', name: 'Bob' }
|
|
95
|
+
* ]);
|
|
96
|
+
*/
|
|
97
|
+
async putBatchObjects<T>(objects: (T & { key: string })[]): Promise<void> {
|
|
98
|
+
await Promise.all(objects.map((obj) => this.putObject(obj)));
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
/**
|
|
102
|
+
* Streams an object upload to the S3 bucket.
|
|
103
|
+
* For compatibility; uses putObject internally.
|
|
104
|
+
* @template T - The type of the object being stored.
|
|
105
|
+
* @param object - The object to stream-upload. Must include a `key` property.
|
|
106
|
+
*/
|
|
107
|
+
async streamUploadObject<T>(object: T & { key: string }): Promise<void> {
|
|
108
|
+
await this.putObject(object);
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
/**
|
|
112
|
+
* Streams multiple object uploads to the S3 bucket.
|
|
113
|
+
* For compatibility; uses putBatchObjects internally.
|
|
114
|
+
* @template T - The type of the objects being stored.
|
|
115
|
+
* @param objects - The objects to stream-upload. Each must include a `key` property.
|
|
116
|
+
*/
|
|
117
|
+
async streamUploadBatchObjects<T>(
|
|
118
|
+
objects: (T & { key: string })[]
|
|
119
|
+
): Promise<void> {
|
|
120
|
+
await this.putBatchObjects(objects);
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
/**
|
|
124
|
+
* Deletes an object from the S3 bucket.
|
|
125
|
+
* @param objectKey - The key of the object to delete.
|
|
126
|
+
*
|
|
127
|
+
* @example
|
|
128
|
+
* await store.deleteObject('user-1');
|
|
129
|
+
*/
|
|
130
|
+
async deleteObject(objectKey: string): Promise<void> {
|
|
131
|
+
await this.s3.send(
|
|
132
|
+
new DeleteObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
133
|
+
);
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
/**
|
|
137
|
+
* Deletes multiple objects from the S3 bucket.
|
|
138
|
+
* @param objectKeys - The keys of the objects to delete.
|
|
139
|
+
*
|
|
140
|
+
* @example
|
|
141
|
+
* await store.deleteBatchObjects(['user-1', 'user-2']);
|
|
142
|
+
*/
|
|
143
|
+
async deleteBatchObjects(objectKeys: string[]): Promise<void> {
|
|
144
|
+
const params: DeleteObjectsCommandInput = {
|
|
145
|
+
Bucket: this.bucket,
|
|
146
|
+
Delete: {
|
|
147
|
+
Objects: objectKeys.map((Key) => ({ Key }))
|
|
148
|
+
}
|
|
149
|
+
};
|
|
150
|
+
await this.s3.send(new DeleteObjectsCommand(params));
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Reads an object from the S3 bucket.
|
|
155
|
+
* @template T - The expected type of the object.
|
|
156
|
+
* @param objectKey - The key of the object to read.
|
|
157
|
+
* @returns The parsed object.
|
|
158
|
+
*
|
|
159
|
+
* @example
|
|
160
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
161
|
+
*/
|
|
162
|
+
async readObject<T>(objectKey: string): Promise<T> {
|
|
163
|
+
const resp = await this.s3.send(
|
|
164
|
+
new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
165
|
+
);
|
|
166
|
+
const body = resp.Body as Readable;
|
|
167
|
+
const chunks: Buffer[] = [];
|
|
168
|
+
for await (const chunk of body) {
|
|
169
|
+
chunks.push(chunk);
|
|
170
|
+
}
|
|
171
|
+
return JSON.parse(Buffer.concat(chunks).toString()) as T;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
/**
|
|
175
|
+
* Reads multiple objects from the S3 bucket.
|
|
176
|
+
* @template T - The expected type of the objects.
|
|
177
|
+
* @param objectKeys - The keys of the objects to read.
|
|
178
|
+
* @returns An array of parsed objects.
|
|
179
|
+
*
|
|
180
|
+
* @example
|
|
181
|
+
* const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);
|
|
182
|
+
*/
|
|
183
|
+
async readBatchObjects<T>(objectKeys: string[]): Promise<T[]> {
|
|
184
|
+
return Promise.all(objectKeys.map((key) => this.readObject<T>(key)));
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
/**
|
|
188
|
+
* Streams an object download from the S3 bucket.
|
|
189
|
+
* @param objectKey - The key of the object to download.
|
|
190
|
+
* @returns A readable stream of the object's contents.
|
|
191
|
+
* @throws If the S3 response does not include a readable stream.
|
|
192
|
+
*
|
|
193
|
+
* @example
|
|
194
|
+
* const stream = await store.streamDownloadObject('user-1');
|
|
195
|
+
* stream.pipe(fs.createWriteStream('user-1.json'));
|
|
196
|
+
*/
|
|
197
|
+
async streamDownloadObject(objectKey: string): Promise<Readable> {
|
|
198
|
+
const resp = await this.s3.send(
|
|
199
|
+
new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
200
|
+
);
|
|
201
|
+
if (!resp.Body || !(resp.Body instanceof Readable)) {
|
|
202
|
+
throw new Error('S3 did not return a stream');
|
|
203
|
+
}
|
|
204
|
+
return resp.Body;
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
/**
|
|
208
|
+
* Streams multiple object downloads from the S3 bucket.
|
|
209
|
+
* @param objectKeys - The keys of the objects to download.
|
|
210
|
+
* @returns An array of readable streams.
|
|
211
|
+
*
|
|
212
|
+
* @example
|
|
213
|
+
* const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);
|
|
214
|
+
* streams[0].pipe(fs.createWriteStream('user-1.json'));
|
|
215
|
+
*/
|
|
216
|
+
async streamDownloadBatchObjects(objectKeys: string[]): Promise<Readable[]> {
|
|
217
|
+
return Promise.all(objectKeys.map((key) => this.streamDownloadObject(key)));
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
/**
|
|
221
|
+
* Gets the underlying S3 client instance.
|
|
222
|
+
* @returns The S3Client instance used by this store.
|
|
223
|
+
*
|
|
224
|
+
* @example
|
|
225
|
+
* const s3Client = store.getClient();
|
|
226
|
+
*/
|
|
227
|
+
getClient(): S3Client {
|
|
228
|
+
return this.s3;
|
|
229
|
+
}
|
|
230
|
+
}
|
package/lib/index.d.mts
ADDED
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
import { S3Client } from '@aws-sdk/client-s3';
|
|
2
|
+
import { OpenTelemetryCollector, MetricsDefinition, TelemetryOptions } from '@forklaunch/core/http';
|
|
3
|
+
import { ObjectStore } from '@forklaunch/core/objectstore';
|
|
4
|
+
import { Readable } from 'stream';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Options for configuring the S3ObjectStore.
|
|
8
|
+
*
|
|
9
|
+
* @example
|
|
10
|
+
* const options: S3ObjectStoreOptions = {
|
|
11
|
+
* bucket: 'my-bucket',
|
|
12
|
+
* clientConfig: { region: 'us-west-2' }
|
|
13
|
+
* };
|
|
14
|
+
*/
|
|
15
|
+
interface S3ObjectStoreOptions {
|
|
16
|
+
/** The S3 bucket name. */
|
|
17
|
+
bucket: string;
|
|
18
|
+
/** Optional existing S3 client instance. */
|
|
19
|
+
client?: S3Client;
|
|
20
|
+
/** Optional configuration for creating a new S3 client. */
|
|
21
|
+
clientConfig?: ConstructorParameters<typeof S3Client>[0];
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* S3-backed implementation of the ObjectStore interface.
|
|
25
|
+
* Provides methods for storing, retrieving, streaming, and deleting objects in S3.
|
|
26
|
+
*
|
|
27
|
+
* @example
|
|
28
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
29
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
30
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
31
|
+
*/
|
|
32
|
+
declare class S3ObjectStore implements ObjectStore<S3Client> {
|
|
33
|
+
private openTelemetryCollector;
|
|
34
|
+
private telemetryOptions;
|
|
35
|
+
private s3;
|
|
36
|
+
private bucket;
|
|
37
|
+
/**
|
|
38
|
+
* Creates a new S3ObjectStore instance.
|
|
39
|
+
* @param openTelemetryCollector - Collector for OpenTelemetry metrics.
|
|
40
|
+
* @param options - S3 configuration options.
|
|
41
|
+
* @param telemetryOptions - Telemetry configuration options.
|
|
42
|
+
*
|
|
43
|
+
* @example
|
|
44
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
45
|
+
*/
|
|
46
|
+
constructor(openTelemetryCollector: OpenTelemetryCollector<MetricsDefinition>, options: S3ObjectStoreOptions, telemetryOptions: TelemetryOptions);
|
|
47
|
+
/**
|
|
48
|
+
* Stores an object in the S3 bucket.
|
|
49
|
+
* @template T - The type of the object being stored.
|
|
50
|
+
* @param object - The object to store. Must include a `key` property.
|
|
51
|
+
*
|
|
52
|
+
* @example
|
|
53
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
54
|
+
*/
|
|
55
|
+
putObject<T>(object: T & {
|
|
56
|
+
key: string;
|
|
57
|
+
}): Promise<void>;
|
|
58
|
+
/**
|
|
59
|
+
* Stores multiple objects in the S3 bucket.
|
|
60
|
+
* @template T - The type of the objects being stored.
|
|
61
|
+
* @param objects - The objects to store. Each must include a `key` property.
|
|
62
|
+
*
|
|
63
|
+
* @example
|
|
64
|
+
* await store.putBatchObjects([
|
|
65
|
+
* { key: 'user-1', name: 'Alice' },
|
|
66
|
+
* { key: 'user-2', name: 'Bob' }
|
|
67
|
+
* ]);
|
|
68
|
+
*/
|
|
69
|
+
putBatchObjects<T>(objects: (T & {
|
|
70
|
+
key: string;
|
|
71
|
+
})[]): Promise<void>;
|
|
72
|
+
/**
|
|
73
|
+
* Streams an object upload to the S3 bucket.
|
|
74
|
+
* For compatibility; uses putObject internally.
|
|
75
|
+
* @template T - The type of the object being stored.
|
|
76
|
+
* @param object - The object to stream-upload. Must include a `key` property.
|
|
77
|
+
*/
|
|
78
|
+
streamUploadObject<T>(object: T & {
|
|
79
|
+
key: string;
|
|
80
|
+
}): Promise<void>;
|
|
81
|
+
/**
|
|
82
|
+
* Streams multiple object uploads to the S3 bucket.
|
|
83
|
+
* For compatibility; uses putBatchObjects internally.
|
|
84
|
+
* @template T - The type of the objects being stored.
|
|
85
|
+
* @param objects - The objects to stream-upload. Each must include a `key` property.
|
|
86
|
+
*/
|
|
87
|
+
streamUploadBatchObjects<T>(objects: (T & {
|
|
88
|
+
key: string;
|
|
89
|
+
})[]): Promise<void>;
|
|
90
|
+
/**
|
|
91
|
+
* Deletes an object from the S3 bucket.
|
|
92
|
+
* @param objectKey - The key of the object to delete.
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* await store.deleteObject('user-1');
|
|
96
|
+
*/
|
|
97
|
+
deleteObject(objectKey: string): Promise<void>;
|
|
98
|
+
/**
|
|
99
|
+
* Deletes multiple objects from the S3 bucket.
|
|
100
|
+
* @param objectKeys - The keys of the objects to delete.
|
|
101
|
+
*
|
|
102
|
+
* @example
|
|
103
|
+
* await store.deleteBatchObjects(['user-1', 'user-2']);
|
|
104
|
+
*/
|
|
105
|
+
deleteBatchObjects(objectKeys: string[]): Promise<void>;
|
|
106
|
+
/**
|
|
107
|
+
* Reads an object from the S3 bucket.
|
|
108
|
+
* @template T - The expected type of the object.
|
|
109
|
+
* @param objectKey - The key of the object to read.
|
|
110
|
+
* @returns The parsed object.
|
|
111
|
+
*
|
|
112
|
+
* @example
|
|
113
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
114
|
+
*/
|
|
115
|
+
readObject<T>(objectKey: string): Promise<T>;
|
|
116
|
+
/**
|
|
117
|
+
* Reads multiple objects from the S3 bucket.
|
|
118
|
+
* @template T - The expected type of the objects.
|
|
119
|
+
* @param objectKeys - The keys of the objects to read.
|
|
120
|
+
* @returns An array of parsed objects.
|
|
121
|
+
*
|
|
122
|
+
* @example
|
|
123
|
+
* const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);
|
|
124
|
+
*/
|
|
125
|
+
readBatchObjects<T>(objectKeys: string[]): Promise<T[]>;
|
|
126
|
+
/**
|
|
127
|
+
* Streams an object download from the S3 bucket.
|
|
128
|
+
* @param objectKey - The key of the object to download.
|
|
129
|
+
* @returns A readable stream of the object's contents.
|
|
130
|
+
* @throws If the S3 response does not include a readable stream.
|
|
131
|
+
*
|
|
132
|
+
* @example
|
|
133
|
+
* const stream = await store.streamDownloadObject('user-1');
|
|
134
|
+
* stream.pipe(fs.createWriteStream('user-1.json'));
|
|
135
|
+
*/
|
|
136
|
+
streamDownloadObject(objectKey: string): Promise<Readable>;
|
|
137
|
+
/**
|
|
138
|
+
* Streams multiple object downloads from the S3 bucket.
|
|
139
|
+
* @param objectKeys - The keys of the objects to download.
|
|
140
|
+
* @returns An array of readable streams.
|
|
141
|
+
*
|
|
142
|
+
* @example
|
|
143
|
+
* const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);
|
|
144
|
+
* streams[0].pipe(fs.createWriteStream('user-1.json'));
|
|
145
|
+
*/
|
|
146
|
+
streamDownloadBatchObjects(objectKeys: string[]): Promise<Readable[]>;
|
|
147
|
+
/**
|
|
148
|
+
* Gets the underlying S3 client instance.
|
|
149
|
+
* @returns The S3Client instance used by this store.
|
|
150
|
+
*
|
|
151
|
+
* @example
|
|
152
|
+
* const s3Client = store.getClient();
|
|
153
|
+
*/
|
|
154
|
+
getClient(): S3Client;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
export { S3ObjectStore };
|
package/lib/index.d.ts
ADDED
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
import { S3Client } from '@aws-sdk/client-s3';
|
|
2
|
+
import { OpenTelemetryCollector, MetricsDefinition, TelemetryOptions } from '@forklaunch/core/http';
|
|
3
|
+
import { ObjectStore } from '@forklaunch/core/objectstore';
|
|
4
|
+
import { Readable } from 'stream';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Options for configuring the S3ObjectStore.
|
|
8
|
+
*
|
|
9
|
+
* @example
|
|
10
|
+
* const options: S3ObjectStoreOptions = {
|
|
11
|
+
* bucket: 'my-bucket',
|
|
12
|
+
* clientConfig: { region: 'us-west-2' }
|
|
13
|
+
* };
|
|
14
|
+
*/
|
|
15
|
+
interface S3ObjectStoreOptions {
|
|
16
|
+
/** The S3 bucket name. */
|
|
17
|
+
bucket: string;
|
|
18
|
+
/** Optional existing S3 client instance. */
|
|
19
|
+
client?: S3Client;
|
|
20
|
+
/** Optional configuration for creating a new S3 client. */
|
|
21
|
+
clientConfig?: ConstructorParameters<typeof S3Client>[0];
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* S3-backed implementation of the ObjectStore interface.
|
|
25
|
+
* Provides methods for storing, retrieving, streaming, and deleting objects in S3.
|
|
26
|
+
*
|
|
27
|
+
* @example
|
|
28
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
29
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
30
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
31
|
+
*/
|
|
32
|
+
declare class S3ObjectStore implements ObjectStore<S3Client> {
|
|
33
|
+
private openTelemetryCollector;
|
|
34
|
+
private telemetryOptions;
|
|
35
|
+
private s3;
|
|
36
|
+
private bucket;
|
|
37
|
+
/**
|
|
38
|
+
* Creates a new S3ObjectStore instance.
|
|
39
|
+
* @param openTelemetryCollector - Collector for OpenTelemetry metrics.
|
|
40
|
+
* @param options - S3 configuration options.
|
|
41
|
+
* @param telemetryOptions - Telemetry configuration options.
|
|
42
|
+
*
|
|
43
|
+
* @example
|
|
44
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
45
|
+
*/
|
|
46
|
+
constructor(openTelemetryCollector: OpenTelemetryCollector<MetricsDefinition>, options: S3ObjectStoreOptions, telemetryOptions: TelemetryOptions);
|
|
47
|
+
/**
|
|
48
|
+
* Stores an object in the S3 bucket.
|
|
49
|
+
* @template T - The type of the object being stored.
|
|
50
|
+
* @param object - The object to store. Must include a `key` property.
|
|
51
|
+
*
|
|
52
|
+
* @example
|
|
53
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
54
|
+
*/
|
|
55
|
+
putObject<T>(object: T & {
|
|
56
|
+
key: string;
|
|
57
|
+
}): Promise<void>;
|
|
58
|
+
/**
|
|
59
|
+
* Stores multiple objects in the S3 bucket.
|
|
60
|
+
* @template T - The type of the objects being stored.
|
|
61
|
+
* @param objects - The objects to store. Each must include a `key` property.
|
|
62
|
+
*
|
|
63
|
+
* @example
|
|
64
|
+
* await store.putBatchObjects([
|
|
65
|
+
* { key: 'user-1', name: 'Alice' },
|
|
66
|
+
* { key: 'user-2', name: 'Bob' }
|
|
67
|
+
* ]);
|
|
68
|
+
*/
|
|
69
|
+
putBatchObjects<T>(objects: (T & {
|
|
70
|
+
key: string;
|
|
71
|
+
})[]): Promise<void>;
|
|
72
|
+
/**
|
|
73
|
+
* Streams an object upload to the S3 bucket.
|
|
74
|
+
* For compatibility; uses putObject internally.
|
|
75
|
+
* @template T - The type of the object being stored.
|
|
76
|
+
* @param object - The object to stream-upload. Must include a `key` property.
|
|
77
|
+
*/
|
|
78
|
+
streamUploadObject<T>(object: T & {
|
|
79
|
+
key: string;
|
|
80
|
+
}): Promise<void>;
|
|
81
|
+
/**
|
|
82
|
+
* Streams multiple object uploads to the S3 bucket.
|
|
83
|
+
* For compatibility; uses putBatchObjects internally.
|
|
84
|
+
* @template T - The type of the objects being stored.
|
|
85
|
+
* @param objects - The objects to stream-upload. Each must include a `key` property.
|
|
86
|
+
*/
|
|
87
|
+
streamUploadBatchObjects<T>(objects: (T & {
|
|
88
|
+
key: string;
|
|
89
|
+
})[]): Promise<void>;
|
|
90
|
+
/**
|
|
91
|
+
* Deletes an object from the S3 bucket.
|
|
92
|
+
* @param objectKey - The key of the object to delete.
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* await store.deleteObject('user-1');
|
|
96
|
+
*/
|
|
97
|
+
deleteObject(objectKey: string): Promise<void>;
|
|
98
|
+
/**
|
|
99
|
+
* Deletes multiple objects from the S3 bucket.
|
|
100
|
+
* @param objectKeys - The keys of the objects to delete.
|
|
101
|
+
*
|
|
102
|
+
* @example
|
|
103
|
+
* await store.deleteBatchObjects(['user-1', 'user-2']);
|
|
104
|
+
*/
|
|
105
|
+
deleteBatchObjects(objectKeys: string[]): Promise<void>;
|
|
106
|
+
/**
|
|
107
|
+
* Reads an object from the S3 bucket.
|
|
108
|
+
* @template T - The expected type of the object.
|
|
109
|
+
* @param objectKey - The key of the object to read.
|
|
110
|
+
* @returns The parsed object.
|
|
111
|
+
*
|
|
112
|
+
* @example
|
|
113
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
114
|
+
*/
|
|
115
|
+
readObject<T>(objectKey: string): Promise<T>;
|
|
116
|
+
/**
|
|
117
|
+
* Reads multiple objects from the S3 bucket.
|
|
118
|
+
* @template T - The expected type of the objects.
|
|
119
|
+
* @param objectKeys - The keys of the objects to read.
|
|
120
|
+
* @returns An array of parsed objects.
|
|
121
|
+
*
|
|
122
|
+
* @example
|
|
123
|
+
* const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);
|
|
124
|
+
*/
|
|
125
|
+
readBatchObjects<T>(objectKeys: string[]): Promise<T[]>;
|
|
126
|
+
/**
|
|
127
|
+
* Streams an object download from the S3 bucket.
|
|
128
|
+
* @param objectKey - The key of the object to download.
|
|
129
|
+
* @returns A readable stream of the object's contents.
|
|
130
|
+
* @throws If the S3 response does not include a readable stream.
|
|
131
|
+
*
|
|
132
|
+
* @example
|
|
133
|
+
* const stream = await store.streamDownloadObject('user-1');
|
|
134
|
+
* stream.pipe(fs.createWriteStream('user-1.json'));
|
|
135
|
+
*/
|
|
136
|
+
streamDownloadObject(objectKey: string): Promise<Readable>;
|
|
137
|
+
/**
|
|
138
|
+
* Streams multiple object downloads from the S3 bucket.
|
|
139
|
+
* @param objectKeys - The keys of the objects to download.
|
|
140
|
+
* @returns An array of readable streams.
|
|
141
|
+
*
|
|
142
|
+
* @example
|
|
143
|
+
* const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);
|
|
144
|
+
* streams[0].pipe(fs.createWriteStream('user-1.json'));
|
|
145
|
+
*/
|
|
146
|
+
streamDownloadBatchObjects(objectKeys: string[]): Promise<Readable[]>;
|
|
147
|
+
/**
|
|
148
|
+
* Gets the underlying S3 client instance.
|
|
149
|
+
* @returns The S3Client instance used by this store.
|
|
150
|
+
*
|
|
151
|
+
* @example
|
|
152
|
+
* const s3Client = store.getClient();
|
|
153
|
+
*/
|
|
154
|
+
getClient(): S3Client;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
export { S3ObjectStore };
|
package/lib/index.js
ADDED
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
|
|
20
|
+
// index.ts
|
|
21
|
+
var index_exports = {};
|
|
22
|
+
__export(index_exports, {
|
|
23
|
+
S3ObjectStore: () => S3ObjectStore
|
|
24
|
+
});
|
|
25
|
+
module.exports = __toCommonJS(index_exports);
|
|
26
|
+
var import_client_s3 = require("@aws-sdk/client-s3");
|
|
27
|
+
var import_stream = require("stream");
|
|
28
|
+
var S3ObjectStore = class {
|
|
29
|
+
/**
|
|
30
|
+
* Creates a new S3ObjectStore instance.
|
|
31
|
+
* @param openTelemetryCollector - Collector for OpenTelemetry metrics.
|
|
32
|
+
* @param options - S3 configuration options.
|
|
33
|
+
* @param telemetryOptions - Telemetry configuration options.
|
|
34
|
+
*
|
|
35
|
+
* @example
|
|
36
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
37
|
+
*/
|
|
38
|
+
constructor(openTelemetryCollector, options, telemetryOptions) {
|
|
39
|
+
this.openTelemetryCollector = openTelemetryCollector;
|
|
40
|
+
this.telemetryOptions = telemetryOptions;
|
|
41
|
+
this.s3 = options.client || new import_client_s3.S3Client(options.clientConfig || {});
|
|
42
|
+
this.bucket = options.bucket;
|
|
43
|
+
}
|
|
44
|
+
s3;
|
|
45
|
+
bucket;
|
|
46
|
+
/**
|
|
47
|
+
* Stores an object in the S3 bucket.
|
|
48
|
+
* @template T - The type of the object being stored.
|
|
49
|
+
* @param object - The object to store. Must include a `key` property.
|
|
50
|
+
*
|
|
51
|
+
* @example
|
|
52
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
53
|
+
*/
|
|
54
|
+
async putObject(object) {
|
|
55
|
+
const { key, ...rest } = object;
|
|
56
|
+
const params = {
|
|
57
|
+
Bucket: this.bucket,
|
|
58
|
+
Key: key,
|
|
59
|
+
Body: JSON.stringify(rest),
|
|
60
|
+
ContentType: "application/json"
|
|
61
|
+
};
|
|
62
|
+
await this.s3.send(new import_client_s3.PutObjectCommand(params));
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Stores multiple objects in the S3 bucket.
|
|
66
|
+
* @template T - The type of the objects being stored.
|
|
67
|
+
* @param objects - The objects to store. Each must include a `key` property.
|
|
68
|
+
*
|
|
69
|
+
* @example
|
|
70
|
+
* await store.putBatchObjects([
|
|
71
|
+
* { key: 'user-1', name: 'Alice' },
|
|
72
|
+
* { key: 'user-2', name: 'Bob' }
|
|
73
|
+
* ]);
|
|
74
|
+
*/
|
|
75
|
+
async putBatchObjects(objects) {
|
|
76
|
+
await Promise.all(objects.map((obj) => this.putObject(obj)));
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Streams an object upload to the S3 bucket.
|
|
80
|
+
* For compatibility; uses putObject internally.
|
|
81
|
+
* @template T - The type of the object being stored.
|
|
82
|
+
* @param object - The object to stream-upload. Must include a `key` property.
|
|
83
|
+
*/
|
|
84
|
+
async streamUploadObject(object) {
|
|
85
|
+
await this.putObject(object);
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Streams multiple object uploads to the S3 bucket.
|
|
89
|
+
* For compatibility; uses putBatchObjects internally.
|
|
90
|
+
* @template T - The type of the objects being stored.
|
|
91
|
+
* @param objects - The objects to stream-upload. Each must include a `key` property.
|
|
92
|
+
*/
|
|
93
|
+
async streamUploadBatchObjects(objects) {
|
|
94
|
+
await this.putBatchObjects(objects);
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Deletes an object from the S3 bucket.
|
|
98
|
+
* @param objectKey - The key of the object to delete.
|
|
99
|
+
*
|
|
100
|
+
* @example
|
|
101
|
+
* await store.deleteObject('user-1');
|
|
102
|
+
*/
|
|
103
|
+
async deleteObject(objectKey) {
|
|
104
|
+
await this.s3.send(
|
|
105
|
+
new import_client_s3.DeleteObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
106
|
+
);
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Deletes multiple objects from the S3 bucket.
|
|
110
|
+
* @param objectKeys - The keys of the objects to delete.
|
|
111
|
+
*
|
|
112
|
+
* @example
|
|
113
|
+
* await store.deleteBatchObjects(['user-1', 'user-2']);
|
|
114
|
+
*/
|
|
115
|
+
async deleteBatchObjects(objectKeys) {
|
|
116
|
+
const params = {
|
|
117
|
+
Bucket: this.bucket,
|
|
118
|
+
Delete: {
|
|
119
|
+
Objects: objectKeys.map((Key) => ({ Key }))
|
|
120
|
+
}
|
|
121
|
+
};
|
|
122
|
+
await this.s3.send(new import_client_s3.DeleteObjectsCommand(params));
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Reads an object from the S3 bucket.
|
|
126
|
+
* @template T - The expected type of the object.
|
|
127
|
+
* @param objectKey - The key of the object to read.
|
|
128
|
+
* @returns The parsed object.
|
|
129
|
+
*
|
|
130
|
+
* @example
|
|
131
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
132
|
+
*/
|
|
133
|
+
async readObject(objectKey) {
|
|
134
|
+
const resp = await this.s3.send(
|
|
135
|
+
new import_client_s3.GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
136
|
+
);
|
|
137
|
+
const body = resp.Body;
|
|
138
|
+
const chunks = [];
|
|
139
|
+
for await (const chunk of body) {
|
|
140
|
+
chunks.push(chunk);
|
|
141
|
+
}
|
|
142
|
+
return JSON.parse(Buffer.concat(chunks).toString());
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Reads multiple objects from the S3 bucket.
|
|
146
|
+
* @template T - The expected type of the objects.
|
|
147
|
+
* @param objectKeys - The keys of the objects to read.
|
|
148
|
+
* @returns An array of parsed objects.
|
|
149
|
+
*
|
|
150
|
+
* @example
|
|
151
|
+
* const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);
|
|
152
|
+
*/
|
|
153
|
+
async readBatchObjects(objectKeys) {
|
|
154
|
+
return Promise.all(objectKeys.map((key) => this.readObject(key)));
|
|
155
|
+
}
|
|
156
|
+
/**
|
|
157
|
+
* Streams an object download from the S3 bucket.
|
|
158
|
+
* @param objectKey - The key of the object to download.
|
|
159
|
+
* @returns A readable stream of the object's contents.
|
|
160
|
+
* @throws If the S3 response does not include a readable stream.
|
|
161
|
+
*
|
|
162
|
+
* @example
|
|
163
|
+
* const stream = await store.streamDownloadObject('user-1');
|
|
164
|
+
* stream.pipe(fs.createWriteStream('user-1.json'));
|
|
165
|
+
*/
|
|
166
|
+
async streamDownloadObject(objectKey) {
|
|
167
|
+
const resp = await this.s3.send(
|
|
168
|
+
new import_client_s3.GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
169
|
+
);
|
|
170
|
+
if (!resp.Body || !(resp.Body instanceof import_stream.Readable)) {
|
|
171
|
+
throw new Error("S3 did not return a stream");
|
|
172
|
+
}
|
|
173
|
+
return resp.Body;
|
|
174
|
+
}
|
|
175
|
+
/**
|
|
176
|
+
* Streams multiple object downloads from the S3 bucket.
|
|
177
|
+
* @param objectKeys - The keys of the objects to download.
|
|
178
|
+
* @returns An array of readable streams.
|
|
179
|
+
*
|
|
180
|
+
* @example
|
|
181
|
+
* const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);
|
|
182
|
+
* streams[0].pipe(fs.createWriteStream('user-1.json'));
|
|
183
|
+
*/
|
|
184
|
+
async streamDownloadBatchObjects(objectKeys) {
|
|
185
|
+
return Promise.all(objectKeys.map((key) => this.streamDownloadObject(key)));
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Gets the underlying S3 client instance.
|
|
189
|
+
* @returns The S3Client instance used by this store.
|
|
190
|
+
*
|
|
191
|
+
* @example
|
|
192
|
+
* const s3Client = store.getClient();
|
|
193
|
+
*/
|
|
194
|
+
getClient() {
|
|
195
|
+
return this.s3;
|
|
196
|
+
}
|
|
197
|
+
};
|
|
198
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
199
|
+
0 && (module.exports = {
|
|
200
|
+
S3ObjectStore
|
|
201
|
+
});
|
|
202
|
+
//# sourceMappingURL=index.js.map
|
package/lib/index.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../index.ts"],"sourcesContent":["import {\n DeleteObjectCommand,\n DeleteObjectsCommand,\n DeleteObjectsCommandInput,\n GetObjectCommand,\n PutObjectCommand,\n PutObjectCommandInput,\n S3Client\n} from '@aws-sdk/client-s3';\nimport {\n MetricsDefinition,\n OpenTelemetryCollector,\n TelemetryOptions\n} from '@forklaunch/core/http';\nimport { ObjectStore } from '@forklaunch/core/objectstore';\nimport { Readable } from 'stream';\n\n/**\n * Options for configuring the S3ObjectStore.\n *\n * @example\n * const options: S3ObjectStoreOptions = {\n * bucket: 'my-bucket',\n * clientConfig: { region: 'us-west-2' }\n * };\n */\ninterface S3ObjectStoreOptions {\n /** The S3 bucket name. */\n bucket: string;\n /** Optional existing S3 client instance. */\n client?: S3Client;\n /** Optional configuration for creating a new S3 client. */\n clientConfig?: ConstructorParameters<typeof S3Client>[0];\n}\n\n/**\n * S3-backed implementation of the ObjectStore interface.\n * Provides methods for storing, retrieving, streaming, and deleting objects in S3.\n *\n * @example\n * const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);\n * await store.putObject({ key: 'user-1', name: 'Alice' });\n * const user = await store.readObject<{ name: string }>('user-1');\n */\nexport class S3ObjectStore implements ObjectStore<S3Client> {\n private s3: S3Client;\n private bucket: string;\n\n /**\n * Creates a new S3ObjectStore instance.\n * @param openTelemetryCollector - Collector for OpenTelemetry metrics.\n * @param options - S3 configuration options.\n * @param telemetryOptions - Telemetry configuration options.\n *\n * @example\n * const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);\n */\n constructor(\n private openTelemetryCollector: OpenTelemetryCollector<MetricsDefinition>,\n options: S3ObjectStoreOptions,\n private telemetryOptions: TelemetryOptions\n ) {\n this.s3 = options.client || new S3Client(options.clientConfig || {});\n this.bucket = options.bucket;\n }\n\n /**\n * Stores an object in the S3 bucket.\n * @template T - The type of the object being stored.\n * @param object - The object to store. Must include a `key` property.\n *\n * @example\n * await store.putObject({ key: 'user-1', name: 'Alice' });\n */\n async putObject<T>(object: T & { key: string }): Promise<void> {\n const { key, ...rest } = object;\n const params: PutObjectCommandInput = {\n Bucket: this.bucket,\n Key: key,\n Body: JSON.stringify(rest),\n ContentType: 'application/json'\n };\n await this.s3.send(new PutObjectCommand(params));\n }\n\n /**\n * Stores multiple objects in the S3 bucket.\n * @template T - The type of the objects being stored.\n * @param objects - The objects to store. Each must include a `key` property.\n *\n * @example\n * await store.putBatchObjects([\n * { key: 'user-1', name: 'Alice' },\n * { key: 'user-2', name: 'Bob' }\n * ]);\n */\n async putBatchObjects<T>(objects: (T & { key: string })[]): Promise<void> {\n await Promise.all(objects.map((obj) => this.putObject(obj)));\n }\n\n /**\n * Streams an object upload to the S3 bucket.\n * For compatibility; uses putObject internally.\n * @template T - The type of the object being stored.\n * @param object - The object to stream-upload. Must include a `key` property.\n */\n async streamUploadObject<T>(object: T & { key: string }): Promise<void> {\n await this.putObject(object);\n }\n\n /**\n * Streams multiple object uploads to the S3 bucket.\n * For compatibility; uses putBatchObjects internally.\n * @template T - The type of the objects being stored.\n * @param objects - The objects to stream-upload. Each must include a `key` property.\n */\n async streamUploadBatchObjects<T>(\n objects: (T & { key: string })[]\n ): Promise<void> {\n await this.putBatchObjects(objects);\n }\n\n /**\n * Deletes an object from the S3 bucket.\n * @param objectKey - The key of the object to delete.\n *\n * @example\n * await store.deleteObject('user-1');\n */\n async deleteObject(objectKey: string): Promise<void> {\n await this.s3.send(\n new DeleteObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n }\n\n /**\n * Deletes multiple objects from the S3 bucket.\n * @param objectKeys - The keys of the objects to delete.\n *\n * @example\n * await store.deleteBatchObjects(['user-1', 'user-2']);\n */\n async deleteBatchObjects(objectKeys: string[]): Promise<void> {\n const params: DeleteObjectsCommandInput = {\n Bucket: this.bucket,\n Delete: {\n Objects: objectKeys.map((Key) => ({ Key }))\n }\n };\n await this.s3.send(new DeleteObjectsCommand(params));\n }\n\n /**\n * Reads an object from the S3 bucket.\n * @template T - The expected type of the object.\n * @param objectKey - The key of the object to read.\n * @returns The parsed object.\n *\n * @example\n * const user = await store.readObject<{ name: string }>('user-1');\n */\n async readObject<T>(objectKey: string): Promise<T> {\n const resp = await this.s3.send(\n new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n const body = resp.Body as Readable;\n const chunks: Buffer[] = [];\n for await (const chunk of body) {\n chunks.push(chunk);\n }\n return JSON.parse(Buffer.concat(chunks).toString()) as T;\n }\n\n /**\n * Reads multiple objects from the S3 bucket.\n * @template T - The expected type of the objects.\n * @param objectKeys - The keys of the objects to read.\n * @returns An array of parsed objects.\n *\n * @example\n * const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);\n */\n async readBatchObjects<T>(objectKeys: string[]): Promise<T[]> {\n return Promise.all(objectKeys.map((key) => this.readObject<T>(key)));\n }\n\n /**\n * Streams an object download from the S3 bucket.\n * @param objectKey - The key of the object to download.\n * @returns A readable stream of the object's contents.\n * @throws If the S3 response does not include a readable stream.\n *\n * @example\n * const stream = await store.streamDownloadObject('user-1');\n * stream.pipe(fs.createWriteStream('user-1.json'));\n */\n async streamDownloadObject(objectKey: string): Promise<Readable> {\n const resp = await this.s3.send(\n new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n if (!resp.Body || !(resp.Body instanceof Readable)) {\n throw new Error('S3 did not return a stream');\n }\n return resp.Body;\n }\n\n /**\n * Streams multiple object downloads from the S3 bucket.\n * @param objectKeys - The keys of the objects to download.\n * @returns An array of readable streams.\n *\n * @example\n * const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);\n * streams[0].pipe(fs.createWriteStream('user-1.json'));\n */\n async streamDownloadBatchObjects(objectKeys: string[]): Promise<Readable[]> {\n return Promise.all(objectKeys.map((key) => this.streamDownloadObject(key)));\n }\n\n /**\n * Gets the underlying S3 client instance.\n * @returns The S3Client instance used by this store.\n *\n * @example\n * const s3Client = store.getClient();\n */\n getClient(): S3Client {\n return this.s3;\n }\n}\n"],"mappings":"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","names":[]}
|
package/lib/index.mjs
ADDED
|
@@ -0,0 +1,183 @@
|
|
|
1
|
+
// index.ts
|
|
2
|
+
import {
|
|
3
|
+
DeleteObjectCommand,
|
|
4
|
+
DeleteObjectsCommand,
|
|
5
|
+
GetObjectCommand,
|
|
6
|
+
PutObjectCommand,
|
|
7
|
+
S3Client
|
|
8
|
+
} from "@aws-sdk/client-s3";
|
|
9
|
+
import { Readable } from "stream";
|
|
10
|
+
var S3ObjectStore = class {
|
|
11
|
+
/**
|
|
12
|
+
* Creates a new S3ObjectStore instance.
|
|
13
|
+
* @param openTelemetryCollector - Collector for OpenTelemetry metrics.
|
|
14
|
+
* @param options - S3 configuration options.
|
|
15
|
+
* @param telemetryOptions - Telemetry configuration options.
|
|
16
|
+
*
|
|
17
|
+
* @example
|
|
18
|
+
* const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);
|
|
19
|
+
*/
|
|
20
|
+
constructor(openTelemetryCollector, options, telemetryOptions) {
|
|
21
|
+
this.openTelemetryCollector = openTelemetryCollector;
|
|
22
|
+
this.telemetryOptions = telemetryOptions;
|
|
23
|
+
this.s3 = options.client || new S3Client(options.clientConfig || {});
|
|
24
|
+
this.bucket = options.bucket;
|
|
25
|
+
}
|
|
26
|
+
s3;
|
|
27
|
+
bucket;
|
|
28
|
+
/**
|
|
29
|
+
* Stores an object in the S3 bucket.
|
|
30
|
+
* @template T - The type of the object being stored.
|
|
31
|
+
* @param object - The object to store. Must include a `key` property.
|
|
32
|
+
*
|
|
33
|
+
* @example
|
|
34
|
+
* await store.putObject({ key: 'user-1', name: 'Alice' });
|
|
35
|
+
*/
|
|
36
|
+
async putObject(object) {
|
|
37
|
+
const { key, ...rest } = object;
|
|
38
|
+
const params = {
|
|
39
|
+
Bucket: this.bucket,
|
|
40
|
+
Key: key,
|
|
41
|
+
Body: JSON.stringify(rest),
|
|
42
|
+
ContentType: "application/json"
|
|
43
|
+
};
|
|
44
|
+
await this.s3.send(new PutObjectCommand(params));
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Stores multiple objects in the S3 bucket.
|
|
48
|
+
* @template T - The type of the objects being stored.
|
|
49
|
+
* @param objects - The objects to store. Each must include a `key` property.
|
|
50
|
+
*
|
|
51
|
+
* @example
|
|
52
|
+
* await store.putBatchObjects([
|
|
53
|
+
* { key: 'user-1', name: 'Alice' },
|
|
54
|
+
* { key: 'user-2', name: 'Bob' }
|
|
55
|
+
* ]);
|
|
56
|
+
*/
|
|
57
|
+
async putBatchObjects(objects) {
|
|
58
|
+
await Promise.all(objects.map((obj) => this.putObject(obj)));
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Streams an object upload to the S3 bucket.
|
|
62
|
+
* For compatibility; uses putObject internally.
|
|
63
|
+
* @template T - The type of the object being stored.
|
|
64
|
+
* @param object - The object to stream-upload. Must include a `key` property.
|
|
65
|
+
*/
|
|
66
|
+
async streamUploadObject(object) {
|
|
67
|
+
await this.putObject(object);
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Streams multiple object uploads to the S3 bucket.
|
|
71
|
+
* For compatibility; uses putBatchObjects internally.
|
|
72
|
+
* @template T - The type of the objects being stored.
|
|
73
|
+
* @param objects - The objects to stream-upload. Each must include a `key` property.
|
|
74
|
+
*/
|
|
75
|
+
async streamUploadBatchObjects(objects) {
|
|
76
|
+
await this.putBatchObjects(objects);
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Deletes an object from the S3 bucket.
|
|
80
|
+
* @param objectKey - The key of the object to delete.
|
|
81
|
+
*
|
|
82
|
+
* @example
|
|
83
|
+
* await store.deleteObject('user-1');
|
|
84
|
+
*/
|
|
85
|
+
async deleteObject(objectKey) {
|
|
86
|
+
await this.s3.send(
|
|
87
|
+
new DeleteObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
88
|
+
);
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* Deletes multiple objects from the S3 bucket.
|
|
92
|
+
* @param objectKeys - The keys of the objects to delete.
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* await store.deleteBatchObjects(['user-1', 'user-2']);
|
|
96
|
+
*/
|
|
97
|
+
async deleteBatchObjects(objectKeys) {
|
|
98
|
+
const params = {
|
|
99
|
+
Bucket: this.bucket,
|
|
100
|
+
Delete: {
|
|
101
|
+
Objects: objectKeys.map((Key) => ({ Key }))
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
await this.s3.send(new DeleteObjectsCommand(params));
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Reads an object from the S3 bucket.
|
|
108
|
+
* @template T - The expected type of the object.
|
|
109
|
+
* @param objectKey - The key of the object to read.
|
|
110
|
+
* @returns The parsed object.
|
|
111
|
+
*
|
|
112
|
+
* @example
|
|
113
|
+
* const user = await store.readObject<{ name: string }>('user-1');
|
|
114
|
+
*/
|
|
115
|
+
async readObject(objectKey) {
|
|
116
|
+
const resp = await this.s3.send(
|
|
117
|
+
new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
118
|
+
);
|
|
119
|
+
const body = resp.Body;
|
|
120
|
+
const chunks = [];
|
|
121
|
+
for await (const chunk of body) {
|
|
122
|
+
chunks.push(chunk);
|
|
123
|
+
}
|
|
124
|
+
return JSON.parse(Buffer.concat(chunks).toString());
|
|
125
|
+
}
|
|
126
|
+
/**
|
|
127
|
+
* Reads multiple objects from the S3 bucket.
|
|
128
|
+
* @template T - The expected type of the objects.
|
|
129
|
+
* @param objectKeys - The keys of the objects to read.
|
|
130
|
+
* @returns An array of parsed objects.
|
|
131
|
+
*
|
|
132
|
+
* @example
|
|
133
|
+
* const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);
|
|
134
|
+
*/
|
|
135
|
+
async readBatchObjects(objectKeys) {
|
|
136
|
+
return Promise.all(objectKeys.map((key) => this.readObject(key)));
|
|
137
|
+
}
|
|
138
|
+
/**
|
|
139
|
+
* Streams an object download from the S3 bucket.
|
|
140
|
+
* @param objectKey - The key of the object to download.
|
|
141
|
+
* @returns A readable stream of the object's contents.
|
|
142
|
+
* @throws If the S3 response does not include a readable stream.
|
|
143
|
+
*
|
|
144
|
+
* @example
|
|
145
|
+
* const stream = await store.streamDownloadObject('user-1');
|
|
146
|
+
* stream.pipe(fs.createWriteStream('user-1.json'));
|
|
147
|
+
*/
|
|
148
|
+
async streamDownloadObject(objectKey) {
|
|
149
|
+
const resp = await this.s3.send(
|
|
150
|
+
new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })
|
|
151
|
+
);
|
|
152
|
+
if (!resp.Body || !(resp.Body instanceof Readable)) {
|
|
153
|
+
throw new Error("S3 did not return a stream");
|
|
154
|
+
}
|
|
155
|
+
return resp.Body;
|
|
156
|
+
}
|
|
157
|
+
/**
|
|
158
|
+
* Streams multiple object downloads from the S3 bucket.
|
|
159
|
+
* @param objectKeys - The keys of the objects to download.
|
|
160
|
+
* @returns An array of readable streams.
|
|
161
|
+
*
|
|
162
|
+
* @example
|
|
163
|
+
* const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);
|
|
164
|
+
* streams[0].pipe(fs.createWriteStream('user-1.json'));
|
|
165
|
+
*/
|
|
166
|
+
async streamDownloadBatchObjects(objectKeys) {
|
|
167
|
+
return Promise.all(objectKeys.map((key) => this.streamDownloadObject(key)));
|
|
168
|
+
}
|
|
169
|
+
/**
|
|
170
|
+
* Gets the underlying S3 client instance.
|
|
171
|
+
* @returns The S3Client instance used by this store.
|
|
172
|
+
*
|
|
173
|
+
* @example
|
|
174
|
+
* const s3Client = store.getClient();
|
|
175
|
+
*/
|
|
176
|
+
getClient() {
|
|
177
|
+
return this.s3;
|
|
178
|
+
}
|
|
179
|
+
};
|
|
180
|
+
export {
|
|
181
|
+
S3ObjectStore
|
|
182
|
+
};
|
|
183
|
+
//# sourceMappingURL=index.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../index.ts"],"sourcesContent":["import {\n DeleteObjectCommand,\n DeleteObjectsCommand,\n DeleteObjectsCommandInput,\n GetObjectCommand,\n PutObjectCommand,\n PutObjectCommandInput,\n S3Client\n} from '@aws-sdk/client-s3';\nimport {\n MetricsDefinition,\n OpenTelemetryCollector,\n TelemetryOptions\n} from '@forklaunch/core/http';\nimport { ObjectStore } from '@forklaunch/core/objectstore';\nimport { Readable } from 'stream';\n\n/**\n * Options for configuring the S3ObjectStore.\n *\n * @example\n * const options: S3ObjectStoreOptions = {\n * bucket: 'my-bucket',\n * clientConfig: { region: 'us-west-2' }\n * };\n */\ninterface S3ObjectStoreOptions {\n /** The S3 bucket name. */\n bucket: string;\n /** Optional existing S3 client instance. */\n client?: S3Client;\n /** Optional configuration for creating a new S3 client. */\n clientConfig?: ConstructorParameters<typeof S3Client>[0];\n}\n\n/**\n * S3-backed implementation of the ObjectStore interface.\n * Provides methods for storing, retrieving, streaming, and deleting objects in S3.\n *\n * @example\n * const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);\n * await store.putObject({ key: 'user-1', name: 'Alice' });\n * const user = await store.readObject<{ name: string }>('user-1');\n */\nexport class S3ObjectStore implements ObjectStore<S3Client> {\n private s3: S3Client;\n private bucket: string;\n\n /**\n * Creates a new S3ObjectStore instance.\n * @param openTelemetryCollector - Collector for OpenTelemetry metrics.\n * @param options - S3 configuration options.\n * @param telemetryOptions - Telemetry configuration options.\n *\n * @example\n * const store = new S3ObjectStore(otelCollector, { bucket: 'my-bucket' }, telemetryOptions);\n */\n constructor(\n private openTelemetryCollector: OpenTelemetryCollector<MetricsDefinition>,\n options: S3ObjectStoreOptions,\n private telemetryOptions: TelemetryOptions\n ) {\n this.s3 = options.client || new S3Client(options.clientConfig || {});\n this.bucket = options.bucket;\n }\n\n /**\n * Stores an object in the S3 bucket.\n * @template T - The type of the object being stored.\n * @param object - The object to store. Must include a `key` property.\n *\n * @example\n * await store.putObject({ key: 'user-1', name: 'Alice' });\n */\n async putObject<T>(object: T & { key: string }): Promise<void> {\n const { key, ...rest } = object;\n const params: PutObjectCommandInput = {\n Bucket: this.bucket,\n Key: key,\n Body: JSON.stringify(rest),\n ContentType: 'application/json'\n };\n await this.s3.send(new PutObjectCommand(params));\n }\n\n /**\n * Stores multiple objects in the S3 bucket.\n * @template T - The type of the objects being stored.\n * @param objects - The objects to store. Each must include a `key` property.\n *\n * @example\n * await store.putBatchObjects([\n * { key: 'user-1', name: 'Alice' },\n * { key: 'user-2', name: 'Bob' }\n * ]);\n */\n async putBatchObjects<T>(objects: (T & { key: string })[]): Promise<void> {\n await Promise.all(objects.map((obj) => this.putObject(obj)));\n }\n\n /**\n * Streams an object upload to the S3 bucket.\n * For compatibility; uses putObject internally.\n * @template T - The type of the object being stored.\n * @param object - The object to stream-upload. Must include a `key` property.\n */\n async streamUploadObject<T>(object: T & { key: string }): Promise<void> {\n await this.putObject(object);\n }\n\n /**\n * Streams multiple object uploads to the S3 bucket.\n * For compatibility; uses putBatchObjects internally.\n * @template T - The type of the objects being stored.\n * @param objects - The objects to stream-upload. Each must include a `key` property.\n */\n async streamUploadBatchObjects<T>(\n objects: (T & { key: string })[]\n ): Promise<void> {\n await this.putBatchObjects(objects);\n }\n\n /**\n * Deletes an object from the S3 bucket.\n * @param objectKey - The key of the object to delete.\n *\n * @example\n * await store.deleteObject('user-1');\n */\n async deleteObject(objectKey: string): Promise<void> {\n await this.s3.send(\n new DeleteObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n }\n\n /**\n * Deletes multiple objects from the S3 bucket.\n * @param objectKeys - The keys of the objects to delete.\n *\n * @example\n * await store.deleteBatchObjects(['user-1', 'user-2']);\n */\n async deleteBatchObjects(objectKeys: string[]): Promise<void> {\n const params: DeleteObjectsCommandInput = {\n Bucket: this.bucket,\n Delete: {\n Objects: objectKeys.map((Key) => ({ Key }))\n }\n };\n await this.s3.send(new DeleteObjectsCommand(params));\n }\n\n /**\n * Reads an object from the S3 bucket.\n * @template T - The expected type of the object.\n * @param objectKey - The key of the object to read.\n * @returns The parsed object.\n *\n * @example\n * const user = await store.readObject<{ name: string }>('user-1');\n */\n async readObject<T>(objectKey: string): Promise<T> {\n const resp = await this.s3.send(\n new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n const body = resp.Body as Readable;\n const chunks: Buffer[] = [];\n for await (const chunk of body) {\n chunks.push(chunk);\n }\n return JSON.parse(Buffer.concat(chunks).toString()) as T;\n }\n\n /**\n * Reads multiple objects from the S3 bucket.\n * @template T - The expected type of the objects.\n * @param objectKeys - The keys of the objects to read.\n * @returns An array of parsed objects.\n *\n * @example\n * const users = await store.readBatchObjects<{ name: string }>(['user-1', 'user-2']);\n */\n async readBatchObjects<T>(objectKeys: string[]): Promise<T[]> {\n return Promise.all(objectKeys.map((key) => this.readObject<T>(key)));\n }\n\n /**\n * Streams an object download from the S3 bucket.\n * @param objectKey - The key of the object to download.\n * @returns A readable stream of the object's contents.\n * @throws If the S3 response does not include a readable stream.\n *\n * @example\n * const stream = await store.streamDownloadObject('user-1');\n * stream.pipe(fs.createWriteStream('user-1.json'));\n */\n async streamDownloadObject(objectKey: string): Promise<Readable> {\n const resp = await this.s3.send(\n new GetObjectCommand({ Bucket: this.bucket, Key: objectKey })\n );\n if (!resp.Body || !(resp.Body instanceof Readable)) {\n throw new Error('S3 did not return a stream');\n }\n return resp.Body;\n }\n\n /**\n * Streams multiple object downloads from the S3 bucket.\n * @param objectKeys - The keys of the objects to download.\n * @returns An array of readable streams.\n *\n * @example\n * const streams = await store.streamDownloadBatchObjects(['user-1', 'user-2']);\n * streams[0].pipe(fs.createWriteStream('user-1.json'));\n */\n async streamDownloadBatchObjects(objectKeys: string[]): Promise<Readable[]> {\n return Promise.all(objectKeys.map((key) => this.streamDownloadObject(key)));\n }\n\n /**\n * Gets the underlying S3 client instance.\n * @returns The S3Client instance used by this store.\n *\n * @example\n * const s3Client = store.getClient();\n */\n getClient(): S3Client {\n return this.s3;\n }\n}\n"],"mappings":"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","names":[]}
|
package/package.json
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@forklaunch/infrastructure-s3",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"description": "S3 infrastructure for ForkLaunch components.",
|
|
5
|
+
"homepage": "https://github.com/forklaunch/forklaunch-js#readme",
|
|
6
|
+
"bugs": {
|
|
7
|
+
"url": "https://github.com/forklaunch/forklaunch-js/issues"
|
|
8
|
+
},
|
|
9
|
+
"repository": {
|
|
10
|
+
"type": "git",
|
|
11
|
+
"url": "git+https://github.com/forklaunch/forklaunch-js.git"
|
|
12
|
+
},
|
|
13
|
+
"license": "MIT",
|
|
14
|
+
"author": "Rohin Bhargava",
|
|
15
|
+
"exports": {
|
|
16
|
+
".": {
|
|
17
|
+
"types": "./lib/src/index.d.ts",
|
|
18
|
+
"import": "./lib/src/index.mjs",
|
|
19
|
+
"require": "./lib/src/index.js",
|
|
20
|
+
"default": "./lib/src/index.js"
|
|
21
|
+
}
|
|
22
|
+
},
|
|
23
|
+
"types": "lib/index.d.ts",
|
|
24
|
+
"directories": {
|
|
25
|
+
"test": "__test__"
|
|
26
|
+
},
|
|
27
|
+
"files": [
|
|
28
|
+
"lib/**"
|
|
29
|
+
],
|
|
30
|
+
"dependencies": {
|
|
31
|
+
"@aws-sdk/client-s3": "^3.821.0",
|
|
32
|
+
"@forklaunch/core": "0.8.3",
|
|
33
|
+
"@forklaunch/common": "0.3.2"
|
|
34
|
+
},
|
|
35
|
+
"devDependencies": {
|
|
36
|
+
"@eslint/js": "^9.27.0",
|
|
37
|
+
"@types/jest": "^29.5.14",
|
|
38
|
+
"globals": "^16.2.0",
|
|
39
|
+
"jest": "^29.7.0",
|
|
40
|
+
"prettier": "^3.5.3",
|
|
41
|
+
"ts-jest": "^29.3.4",
|
|
42
|
+
"ts-node": "^10.9.2",
|
|
43
|
+
"tsup": "^8.5.0",
|
|
44
|
+
"typedoc": "^0.28.5",
|
|
45
|
+
"typescript": "^5.8.3",
|
|
46
|
+
"typescript-eslint": "^8.33.0"
|
|
47
|
+
},
|
|
48
|
+
"scripts": {
|
|
49
|
+
"build": "tsc --noEmit && tsup ./index.ts --format cjs,esm --no-splitting --dts --tsconfig tsconfig.json --out-dir lib --clean --sourcemap && if [ -f eject-infrastructure-package.bash ]; then pnpm package:eject; fi",
|
|
50
|
+
"clean": "rm -rf lib pnpm.lock.yaml node_modules",
|
|
51
|
+
"docs": "typedoc --out docs *",
|
|
52
|
+
"format": "prettier --ignore-path=.prettierignore --config .prettierrc '**/*.{ts,tsx,json}' --write",
|
|
53
|
+
"lint": "eslint . -c eslint.config.mjs",
|
|
54
|
+
"lint:fix": "eslint . -c eslint.config.mjs --fix",
|
|
55
|
+
"package:eject": "./eject-infrastructure-package.bash s3",
|
|
56
|
+
"publish:package": "./publish-package.bash",
|
|
57
|
+
"test": "vitest --passWithNoTests"
|
|
58
|
+
}
|
|
59
|
+
}
|