I managed to use aws-sdk-mock
with Jest in the end (although I am using Typescript as well):
Going to put my code up here in case it helps anyone in the future:
DynamoDBAdapter.ts
```
import DynamoDB from "aws-sdk/clients/dynamodb";
import { get, isEmpty, map } from "lodash";
import ExternalError from “…/errors/ExternalError”;
import ResourceNotFoundError from “…/errors/ResourceNotFoundError”;
import ValidationError from “…/errors/ValidationError”;
export interface IDynamoDBItemKey {
[name: string]: string;
}
export default class DynamoDBAdapter {
protected client: DynamoDB.DocumentClient;
constructor(client: DynamoDB.DocumentClient) {
this.client = client;
}
public scan = (tableName: string, limit: number = 100) => {
return this.client.scan({
Limit : limit,
TableName : tableName,
}).promise();
}
public query = (tableName: string, keys: IDynamoDBItemKey, limit: number = 100) => {
const [ hashKey, rangeKey ] = Object.keys(keys);
const hasRangedKey = Object.keys(keys).length === 2 && typeof rangeKey !== "undefined";
const expressionAttributeValues: { [name: string]: string } = { ":hkey" : keys[hashKey] };
let keyConditionExpression = `${hashKey} = :hkey`;
if (hasRangedKey) {
keyConditionExpression += ` and ${rangeKey} > :rkey`;
expressionAttributeValues[":rkey"] = keys[rangeKey];
}
return this.client.query({
ExpressionAttributeValues : expressionAttributeValues,
KeyConditionExpression : keyConditionExpression,
Limit : limit,
TableName : tableName,
}).promise();
}
public batchGet = (tableName: string, keyName: string, keyValues: string[]) => {
const formattedKeys = map(keyValues, (value) => { return { [keyName] : value }; });
return this.client.batchGet({
RequestItems : {
[tableName] : {
Keys : formattedKeys,
},
},
}).promise();
}
public get = (tableName: string, key: IDynamoDBItemKey) => {
return this.client.get({
Key : key,
TableName : tableName,
})
.promise();
}
public put = (tableName: string, item: T): Promise => {
return this.client.put({
Item : item,
TableName : tableName,
})
.promise()
.then(() => {
return item;
});
}
public delete = (tableName: string, key: IDynamoDBItemKey): Promise => {
return this.client.delete({
Key : key,
TableName : tableName,
}).promise()
.then(() => {
return;
});
}
}
</details>
<details>
<summary> <code>DynamoDBAdapter.spec.ts</code> </summary>
import AWS from “aws-sdk”;
import MockAWS from “aws-sdk-mock”;
import DynamoDBAdapter from “…/…/src/adapters/DynamoDBAdapter”;
MockAWS.setSDKInstance(AWS);
describe(“DynamoDBAdapter”, () => {
let adapter: DynamoDBAdapter;
describe("#batchGet", () => {
beforeAll(() => {
MockAWS.mock("DynamoDB.DocumentClient", "batchGet", Promise.resolve().then(() => {
return {
Responses: {
tableName: [
{ foo : "bar" },
{ foo : "baz" },
{ foo : "quux" },
],
},
};
}));
adapter = new DynamoDBAdapter(new AWS.DynamoDB.DocumentClient);
});
afterAll(() => {
AWS.restore("DynamoDB.DocumentClient");
});
it("can retrieve a batch of items in DynamoDB", () => {
return adapter.batchGet("tableName", "foo", [ "bar", "baz", "quux" ])
.then((response) => {
expect(response).toHaveProperty("Responses");
expect(response.Responses).toHaveProperty("tableName");
expect(response.Responses.tableName).toHaveLength(3);
});
});
});
describe("#get", () => {
beforeAll(() => {
MockAWS.mock("DynamoDB.DocumentClient", "get", Promise.resolve().then(() => {
return {
Item: {
foo : "bar",
}
};
}));
adapter = new DynamoDBAdapter(new AWS.DynamoDB.DocumentClient);
});
afterAll(() => {
AWS.restore("DynamoDB.DocumentClient");
});
it("can retrieve an item in DynamoDB", () => {
return adapter.get("tableName", { foo: "bar" })
.then((response) => {
expect(response).toHaveProperty("Item");
expect(response.Item).toHaveProperty("foo");
expect(response.Item.foo).toEqual("bar");
});
});
});
describe("#put", () => {
beforeAll(() => {
MockAWS.mock("DynamoDB.DocumentClient", "put", Promise.resolve());
adapter = new DynamoDBAdapter(new AWS.DynamoDB.DocumentClient);
});
afterAll(() => {
AWS.restore("DynamoDB.DocumentClient");
});
it("can put an item in DynamoDB", () => {
return adapter.put("tableName", { foo: "bar" })
.then((response) => {
expect(response).toEqual({ foo: "bar" });
});
});
});
describe("#delete", () => {
beforeAll(() => {
MockAWS.mock("DynamoDB.DocumentClient", "delete", Promise.resolve());
adapter = new DynamoDBAdapter(new AWS.DynamoDB.DocumentClient);
});
afterAll(() => {
AWS.restore("DynamoDB.DocumentClient");
});
it("can delete an item in DynamoDB", () => {
return adapter.delete("tableName", { foo: "bar" })
.then((response) => {
expect(response).toBeUndefined();
});
});
});
});
</details>