Home / Blogs / Node.js

Checks to make before a REST handler ships

The response is not proof that the write happened.

This list is shorter than a style guide. It is the set of mistakes that turn into a broken screen or a row shown to the wrong person.

The handler

  • Validate the body before any write. Drop or reject unknown fields. Do not copy req.body onto the model.
  • Name the columns in the query.
  • Use the status codes the spec lists. A thrown error that becomes a generic 500 needs a test for the real code, then a fix for the mapping.
  • If the row has an owner, check the row, not only the role. That is the same rule as the JWT checks.
const body = schema.parse(req.body);
const [count] = await Record.update(
  { status: body.status },
  { where: { id: req.params.id, ownerId: req.user.id } },
);
if (count !== 1) return res.status(404).json({ error: "not_found" });

Putting the owner in the WHERE clause means a stranger's valid token changes zero rows. The handler does not load the record, forget the check, and save.

The test

One test for the happy write. One for a bad body. One for the wrong user. The happy test reads the row back from the database. It does not trust the JSON the handler just returned. A success body and a failed commit can happen in the same request.

The spec and the log

The OpenAPI entry matches the test, which is the bar from failing CI when the spec drifts. Logs carry a request id, the subject, and the status. They do not carry the body of a private record, and they do not carry the token.

If you cannot point at those, the route is a draft, including when the screen that calls it is already in review.

Topics Node.js