Skip to content
Get AI Business OS

State Files Explained

PRIMA Project Management

PRIMA Project Management keeps your project register in one file, .claude/state/state.json. Every command reads it, /night and the project-tracking skill write to it, and the dashboard draws from it. This page explains what the file holds and how the product protects it.

File Purpose
.claude/state/state.json Your project register, the single source of truth for your projects
.claude/state/state.schema.json The rules the register must follow, installed by the product
.claude/state/backups/YYYY-MM-DD.json One backup of the register per day
.claude/state/history/YYYY-MM.json The session history archive, one file per month
.claude/state/projects/P###.json Optional detail file for one project, read by the dashboard
.claude/state/tasks/P###.json Optional task file for one project, read by the dashboard
.claude/config/integrations.json Your calendar, meetings, storage and project numbering settings

state.json and integrations.json belong to you, and a product update never overwrites them. The schema is a protected product file that an update replaces.

Field Required Contents
version Yes The schema version, such as 1.0.0
workspace Yes The workspace identity (see below)
projects Yes One entry for each project, archived projects included
nextProjectNumber No The next project number, raised by one after each new project
sessionHistory No This calendar month’s session summaries, newest first, written by /night. Earlier months move to the monthly archive
priorities No Three lists, immediate, thisWeek and upcoming
pendingItems No Items that need a project home or a decision
recentWork No Three to five activities from the latest session, replaced by each /night
selectedCalendars No The calendars /day reads, each with an id and a name

The workspace object names the workspace and guards your git pushes.

Field Required Contents
name Yes The workspace name, such as Example Consulting
id Yes A short identifier in lower-case letters, numbers and hyphens, such as example-consulting
type Yes personal, client or internal
githubRepo No The GitHub repository in owner/repo form, or an empty string when there is none
owner No The name shown on the dashboard’s sidebar card

When githubRepo holds a value, /sync and /night compare it with your git remote before every push and stop when the two differ. Rules It Installs explains the check.

{
"id": "P012",
"name": "Spring Workshop",
"description": "Half-day workshop for the spring intake",
"status": "in-progress",
"priority": "medium",
"category": "client",
"tags": ["training", "events"],
"created": "2026-09-01",
"startDate": "2026-09-01",
"dueDate": "2026-11-20",
"milestones": [
{ "name": "Venue confirmed", "date": "2026-10-10", "status": "done" },
{ "name": "Materials ready", "date": "2026-11-13", "status": "pending" }
],
"lastWorked": "2026-10-13",
"stoppedAt": "Outline drafted, next is the exercises section",
"lastAction": "Drafted the session outline",
"pausedReason": null,
"path": "Domains/15 Education & Training/P012 Spring Workshop",
"domain": "15 Education & Training",
"notes": ""
}
Field Required Contents
id Yes The project ID, never reused and never given a new meaning
name Yes The project name
status Yes in-progress, paused, overdue or archived
category Yes One of client, product, internal, marketing, research, operations, finance, sales, legal or it
priority No high, medium or low
tags No Free labels for themes that cut across projects
created No The date the project was created
startDate, dueDate No The delivery dates the timeline draws
milestones No Each with a name, a date and a status of pending or done
lastWorked No The last date work was recorded
stoppedAt No Where work stopped, set by /night and cleared when you next work on the project
lastAction No The last completed action, set by /night
pausedReason No Why the project is paused, needed when the status is paused
path No The project folder, relative to the workspace
domain No The domain folder, in workspaces that use Domains/
description, notes No Free text

A milestone moves from pending to done only, and never back.

An ID is a prefix of one to ten letters, an optional hyphen and three to six digits, such as P012 or PRJ-0012. The default is P with three digits. The IDs already in your register decide the format for new projects. Creating a Project explains how the next number is chosen.

Some workspaces keep the longer fields for each project in a separate detail file under .claude/state/projects/. When that folder exists, the dashboard reads the description, notes, stoppedAt, lastAction, milestones and similar fields from the project’s own file. When the folder does not exist, it reads them from the project’s entry in state.json.

Before every write to the register, Claude runs Scripts/backup-state.sh. The script copies state.json to .claude/state/backups/ under the current date, so a later write on the same day replaces that day’s copy. Each run also deletes backups older than 30 days.

Keep .claude/state/backups/ out of your commits, which the AI Business OS .gitignore already does by listing the folder.

The session history in state.json holds the current calendar month only. After each /night, Scripts/archive-history.sh moves every entry from an earlier month into the archive file for that month, such as .claude/state/history/2026-07.json, so no entry is ever deleted. On the first /night of a new month, the whole of the previous month moves to its file. Each archived entry keeps its date and summary and gains an archivedFrom field that names the workspace or the project it came from. The same applies to the history of each project, in state.json and in any detail files.

You can run the script yourself from the workspace folder. With --dry-run it reports what it would move and changes nothing.

Terminal window
Scripts/archive-history.sh --dry-run

After every write, Claude runs Scripts/validate-state.sh. You can also run it yourself from the workspace folder at any time.

Terminal window
Scripts/validate-state.sh
✅ JSON syntax valid
✅ Required fields present (version: 1.0.0)
✅ Project IDs unique
✅ Project ID format valid
✅ Status values valid
✅ Projects: 6 total (4 active, 1 paused, 1 overdue, 0 archived)
ℹ️ ajv-cli not installed — schema validation skipped (install: npm install -g ajv-cli)
✅ State validation passed

An error stops the script and fails the check. Errors cover broken JSON, a missing version, workspace or projects field, an invalid workspace type, a duplicate project ID, an ID in the wrong format and a status outside the four allowed values. Warnings let the check pass. They cover an incomplete workspace identity, a duplicate project name, a mixed ID format, a missing or unknown category, a paused project with no reason and a session history that still holds entries from an earlier month. An archive file in .claude/state/history/ without an entries list is an error.

When ajv-cli is installed, the script also checks the whole file against the schema, and a schema failure is an error. When a write fails validation, Claude restores the backup and reports the error.

  1. Look in .claude/state/backups/ for the most recent copy from before the problem began.
  2. Copy that backup over your register, replacing the date in the command with the backup’s date.
  3. Run the validation script to confirm the restored file passes its checks.
Terminal window
cp .claude/state/backups/2026-10-13.json .claude/state/state.json
Scripts/validate-state.sh