Testing Azure Functions v4 Node & TypeScript with Jest

To write and run tests for Azure Functions with Node / Typescript, we need a bit of extra setup. We’ll start with a new function project with an http trigger and then add the required dependencies:

npm install --save-dev jest typescript ts-jest @types/jest ts-node

I added ts-node as an additional dependency which is not listed in the ts-jest Getting started but required to run the tests.

Instead of initializing the config over the cli I prefer to base mine on the ts-jest preset in the jest.config.ts like this:

import type { Config } from "jest";

const config: Config = {
  preset: "ts-jest",
  testEnvironment: "node",
  verbose: true,
  rootDir: "./",
  testMatch: ["**/tests/**/*.test.ts"],
  testPathIgnorePatterns: ["/node_modules/", "/dist/"],
};

export default config;

Afterwards we update the package.json with the test command:

{
...
  "scripts": {
    "build": "tsc",
    "watch": "tsc -w",
    "clean": "rimraf dist",
    "prestart": "npm run clean && npm run build",
    "start": "func start",
    "test": "jest --config jest.config.ts"
  },
...
}

Testing http trigger functions

To actually test http functions we can use the HttpRequestInit interface for simplified mocking of the test request. A simple test with a request body could look something like this:

  it("should return the sum for valid POST requests", async () => {
    const requestInit: HttpRequestInit = {
      method: "POST",
      url: "http://localhost:7071/api/sum",
      headers: {
        "Content-Type": "application/json",
      },
      body: { string: JSON.stringify({ a: 5, b: 3 }) },
    };
    const mockRequest = new HttpRequest(requestInit);
    const response = await sum(mockRequest, mockContext);

    expect(response.status).toBe(200);
    expect(response.jsonBody).toEqual({ sum: 8 });
  });

Finally, to run the tests we simply call:

npm run test

Note

You will see some warnings that @azure/functions is running in test mode, but for me that’s absolutely fine since I want to test my business logic and not the function runtime itself.

You can find the full source code for this basic setup over on GitHub.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.