@omersalkanovic/nestjs-dynamodb
v0.4.7
Published
NestJS DynamoDB Client - Fork
Downloads
13
Readme
NestJS DynamoDB
Description
Opinated way to use DynamoDB with NestJS and typescript, heavily inspired by nestjs-typed-dynamodb
Getting Started
First install this module
npm install @omersalkanovic/nestjs-dynamodb
Notice that it will install dynamodb-data-mapper-annotations as a dependency
Usage
In order to create a DynamoDB connection
app.module.ts
import { Module } from '@nestjs/common'
import { TypegooseModule } from 'nestjs-typed-dynamodb'
import { CatsModule } from './cat.module.ts'
@Module({
imports: [
DynamoDBModule.forRoot({
AWSConfig: {
region: 'local',
accessKeyId: 'null',
secretAccessKey: 'null',
},
dynamoDBOptions: {
endpoint: 'localhost:8000',
sslEnabled: false,
region: 'local-env',
},
}),
CatsModule,
],
})
export class ApplicationModule {}
To insert records to Dynamo, you first need to create your table, for this we use dynamodb-data-mapper-annotations (under the hood). Every decorator in that package is exposed in this package as well BUT CAPITALIZED .
cat.schema.ts
import {
Attribute,
AutoGeneratedHashKey,
RangeKey,
Table,
VersionAttribute,
} from '@omersalkanovic/nestjs-dynamodb'
import * as nanoid from 'nanoid'
@Table('cat')
class Cat {
@RangeKey({ defaultProvider: nanoid })
id: string
@HashKey()
breed: string
@Attribute()
age: number
@Attribute()
alive?: boolean
// This property will not be saved to DynamoDB.
notPersistedToDynamoDb: string
}
Note: nanoid is only used a way to assign a random id, feel free to use whatever you want
cats.service.ts
import { Injectable } from '@nestjs/common'
import { ReturnModel, InjectModel, OR } from '@omersalkanovic/nestjs-dynamodb'
import { Cat } from './cat.schema'
import { CatInput } from './cat.input'
const ReturnModel = ReturnModel<Cat>()
@Injectable()
export class CatsService {
constructor(
@InjectModel(Cat)
private readonly catModel: typeof ReturnModel,
) {}
async findAll(): Promise<Cat[]> {
return this.catModel.find()
}
async findById(id: string): Promise<Cat> {
return this.catModel.findById(id)
}
async create(input: CatInput): Promise<Cat> {
return this.catModel.create(input)
}
async delete(input: string): Promise<DynamoDB.DeleteItemOutput> {
return this.catModel.findByIdAndDelete(input)
}
async update(id: string, item: CatInput): Promise<Cat> {
return this.catModel.findByIdAndUpdate(id, item)
}
async find(input: Partial<CatInput>): Promise<Cat[]> {
return this.catModel.find(input);
}
}
Now its to much easily to query through dynamoDB If you have arrays and different objects
async find(input: Partial<CatInput>): Promise<Cat[]> {
return this.catModel.find({alive: true, age: OR(19)});
// {
// TableName: 'cat',
// ExpressionAttributeValues: {
// ':aliveValue': { BOOL: true },
// ':ageValue': { N: 19 },
// },
// FilterExpression: 'alive = :aliveValue OR age = :ageValue'
// }
async find(input: Partial<CatInput>): Promise<Cat[]> {
return this.catModel.find({alive: true, age: [10, 12]});
// {
// TableName: 'cat',
// ExpressionAttributeValues: {
// ':aliveValue': { BOOL: true },
// ':ageValue0': { N: 10 },
// ':ageValue1': { N: 12 },
// },
// FilterExpression: 'alive = :aliveValue AND (age = :ageValue0 OR age = :ageValue1)'
// }
}
Now you can use your service as you wish!
Async configuration
app.module.ts
import { Module } from '@nestjs/common'
import { TypegooseModule } from 'nestjs-typegoose'
import { Cats } from './cat.schema'
@Module({
imports: [
DynamoDBModule.forRootAsync({
imports: [ConfigModule],
useFactory: async (config: ConfigService) => ({
AWSConfig: {
region: 'local',
accessKeyId: 'null',
secretAccessKey: 'null',
},
dynamoDBOptions: {
endpoint: config.get<string>('DYNAMODB_URL', 'localhost:8000'),
sslEnabled: false,
region: 'local-env',
},
}),
inject: [ConfigService],
}),
],
})
export class ApplicationModule {}