# Example contract — niche job board

Free worked example by PlanSmith, 28 September 2026.
https://plansmith.io/blog/claude-md-template-for-saas
Adapt for your own project. This is a sample scope, not an audited application.

## Scope

Build a board where employers submit listings for admin approval and candidates
apply on site. Free listings only. Exclude billing, subscriptions, resume search,
chat and algorithmic matching from this example. Choose the niche before work.

Use the repository's existing stack. Before coding, confirm its install, dev,
build and test commands and decide retention and administrator access policy.

## Roles and ownership

- Visitor: read published jobs only.
- Candidate: maintain own profile, submit own application, withdraw it.
- Employer: manage jobs belonging to its organisation and read applications
  for those jobs, subject to the withdrawal policy.
- Admin: approve/reject publication and moderate jobs. Applicant access is
  denied unless an explicit, logged exception is added to the accepted scope.

Every job has an employer organisation ID. Every application has a job ID and
candidate ID. Authorize list, detail, edit, export and attachment requests on
the server. Signing up or changing a request parameter must not grant a role.

## Lifecycles

Job: Draft → Pending review → Published or Rejected. Rejected jobs can return
to Draft. Published jobs can become Closed or Expired. Employers can close
their own jobs. Only administrators can publish. Decide whether editing a
published job requires another review before implementing that path.

Application: Submitted → Withdrawn by its candidate. Employer review state is
separate. In this example withdrawal removes employer access to the applicant's
contact details and resume immediately. Retention of audit metadata needs a
separate documented decision. Do not imply a withdrawal deletes all records.

Reject a second active application from the same candidate to the same job.
Recheck publication and expiry on the server at submission time.

## Build sequence

1. Identity, organisation membership and deny-by-default ownership checks.
2. Create draft → review → publish → close, with a public published-only list.
3. Apply → persist → owning employer review → candidate withdrawal.
4. Search, filters, error/empty states and scoped exports if approved.
5. Deployed verification, operational checks and a release receipt.

## Acceptance fixtures

Use Employer A/Job A, Employer B/Job B, Candidate One and Candidate Two.
Never use real applicant information in the demo.

- Employer A creates and reads Job A successfully.
- Employer B cannot read or modify Job A's draft via UI or direct API.
- Candidate One applies to Job A; the saved application survives a reload.
- Employer A can read that application and its resume.
- Employer B, Candidate Two and a signed-out visitor cannot read either.
- Closing Job A rejects a submission from a page opened before closure.
- Repeated submit does not create a duplicate application.
- Withdrawal removes employer contact/resume access through UI, API and file URL.
- Public search and sitemap never expose drafts or private application URLs.

## Verification and handoff

Record actual commands, actor, expected result, observed result and evidence.
Mark skipped checks Not tested. Distinguish local results from live release
results. Test email delivery, keyboard/phone use and a backup restore separately.

Do not claim this example implements payments or proves production readiness.
For paid listings, extend the contract first with verified payment events,
idempotent entitlement grants, moderation, refunds and reconciliation.
