Skip to main content
EngineeringHigher education

Why an assessment marketing site belongs on a static host

Static hosting removes a class of outage from the pages candidates see first, and costs less than the runtime it replaces.

2 min read

ST

Written by

Seratlas Team

Engineering and delivery

2 min read

We build and operate assessment software. We write here about the parts that are harder than they look.

An assessment platform has two very different kinds of page. The application is stateful, authenticated, and has to be correct under load during an exam window. The marketing site is none of those things: it is the same twenty pages for every visitor, and its worst failure mode is being unreachable on the morning of a procurement call.

Treating the second like the first is how a marketing page ends up sharing an outage with a grading queue.

What "static" actually removes

A static export has no runtime on the origin. There is no Node process, no connection pool, and no request-time rendering, so an entire category of incident simply cannot occur — the page cannot be slow because something else is busy.

The trade is real but narrow: every page must be knowable at build time.

Things that stay possible

  • Forms, by posting to an endpoint from the browser.
  • Search, if the index is small enough to ship.
  • Anything time-based that can tolerate being as fresh as the last deploy.

Things that do not

  • Per-visitor content above the fold.
  • Redirects that depend on request state.
  • Anything that needs a secret at request time.

That last one deserves emphasis. On a static site there is no server to hide a credential in, so any value the page needs is a value the visitor can read.

The build becomes the risky step

Moving rendering to build time does not delete the risk, it relocates it. A mistake that used to surface as a 500 on one page now surfaces as a bad deploy across all of them, and a build that reads content off disk will happily produce a page with nothing on it if the read silently fails.

// Validate at the boundary, and name the file in the error.
const result = schema.safeParse(frontmatter);
if (!result.success) {
  throw new Error(`Invalid frontmatter in ${filename}`);
}

Failing the build is the correct response to unparseable content. A page that renders with a missing field is the outcome worth avoiding, because it looks fine in CI and wrong in production.

Where the savings actually come from

Not from the hosting bill, which was never the largest line. They come from the work that stops existing: no runtime to patch, no scaling policy to tune, no health check to page someone at 3am, and a deploy whose rollback is re-uploading the previous directory.

What to keep an eye on

Cache invalidation and the trailing-slash rules are the two details that bite. Both are configuration rather than code, which means neither is covered by your tests, and both fail in ways that only appear from outside your network.

Test the deployed URL, not the build output.

Common questions

No. A form posts to a third-party endpoint from the browser, so there is nothing to run on the origin. What you give up is server-side validation, which means the endpoint has to do its own.

Those belong in the application, behind a login, not on the marketing site. Splitting them is usually a simplification rather than a compromise.

Building something like this?

If any of the above is a problem you are currently having, we are happy to talk about it without a sales process attached.