
Write the review from the goals your team already set in 15Five
PerfCopilot reads the 15Five objectives and key results each person owned during the cycle you are reviewing, then drafts a performance review where every claim about goal progress comes from that synced goal data and is tagged with the source it came from, bias-checked before a manager sees it. The credential is a read-only API token you generate in your own 15Five account, and nothing is ever written back into 15Five.
Connect 15Five and draft a review → · read-only, no credit card, no seat minimum
✓ Objectives with their nested key results · ✓ Every goal claim tagged to its source · ✓ Bias-checked before you send
If your team already writes objectives in 15Five, those objectives are the clearest statement of what each person was asked to do this period. They are also the thing managers most often retype from memory at review time, which is where the vagueness starts. This page is about the alternative: reading them directly, one employee at a time, and keeping the review's sentences anchored to that record rather than to a manager's recollection of it.
What PerfCopilot reads from 15Five
One endpoint carries the whole sync. PerfCopilot asks 15Five for the objectives owned by a single person, reads the key results nested inside each one, and stops there.
GET /api/public/objectives/?owner=<one employee>&page_size=200
from each objective name, description, status,
start_date / end_date (falling back to
created_at / due_date when those are absent)
from each key result id, name, status,
target_value (or target)
The base URL defaults to https://my.15five.com/api/public and the response is read as a paged list, so a tenant on a different host is a configuration change rather than a code change. Three things follow from that shape, and each one matters at review time:
- An objective becomes a goal record, keyed to the 15Five object. We store it against the id 15Five gave it, so running the sync again updates the title, description, status and dates that moved and leaves everything else alone. Syncing twice does not give an employee twice the goals.
- Key results stay attached to their parent, in order. Each key result keeps its own title, target and status under the objective it belongs to, which is what lets a draft say which part of an objective landed and which part did not.
- The owner filter is strict. The query asks for one person's objectives, so goals belong to the employee 15Five says owns them rather than to whoever ran the sync.
How a 15Five status becomes a review status
15Five and PerfCopilot do not use the same words for how a goal is going, so the sync maps one onto the other. The mapping is fixed and worth knowing before you read a draft:
| Status in 15Five | Status in PerfCopilot |
|---|---|
achieved, completed, done | completed |
behind, at_risk | at risk |
needs_attention, off_track, missed | off track |
on_track, or anything unrecognised | on track |
Two deliberate choices sit in that table. needs_attention maps to off track rather than at risk, because in 15Five's own workflow it is the state asking for the most intervention, and rounding it down would flatter the review. And an unrecognised value reads as on track rather than failing the sync, which keeps a 15Five release from breaking a review cycle, at the cost of looking optimistic. If your team uses custom statuses, read a draft with that in mind.
PerfCopilot can also roll an objective's status up from its key results, computed at every read rather than cached: all key results completed reads as completed, any one off track makes the objective off track, any one at risk makes it at risk, and otherwise it is on track. That roll-up does not run on a 15Five objective. Every goal the sync writes is given an explicit status, taken from the mapping above and stored on the goal record, and an explicit status always wins over the roll-up. The roll-up is reachable only for goals a manager types into PerfCopilot by hand and leaves without a status of their own.
The consequence deserves saying plainly: because a missing status maps to on track, an objective that 15Five sends with no status at all is stored and shown as on track even when every key result under it is off track. That is the same optimism as the unrecognised-status row above, arriving from the other direction. If an objective's status reads kinder than its key results, the status came from 15Five, and the key results are the line to read.
Which objectives count toward the cycle you are reviewing
An objective counts for a review cycle when its period overlaps the cycle's period, inclusive at both ends. That is the rule, and it is more useful than a tidier one: a half-year objective that straddles the start of a quarter is part of what that quarter's review should discuss, so it is included rather than dropped for starting too early.
When 15Five supplies no dates at all, the first sync gives the goal a window of the day it arrived plus the next 90 days, and only on first creation. A later sync will not move those dates unless 15Five actually sends new ones. That is a small thing with a real consequence: a date that drifted on every sync would quietly move goals in and out of review periods behind the manager's back.
When you run Sync All for a cycle, every overlapping goal is also mirrored into that cycle's signal strip and stamped no later than the cycle's end date, rebuilt from scratch on each run. That is what lets you see the goal coverage a review will be written from before you generate anything.
What the draft actually does with an objective
The model that writes the review does not get a goals dashboard. It gets the objectives and key results for the cycle, as structured data, inside the block of available performance data:
[GOALS DATA]
[
{
"title": "Cut onboarding time for new accounts",
"description": "Get a new account to first value without a call.",
"period_start": "2026-07-01",
"period_end": "2026-09-30",
"status": "completed",
"key_results": [
{ "title": "Median setup under 3 days", "target": "3", "progress_percent": null, "status": "completed" },
{ "title": "Self-serve guide published", "target": null, "progress_percent": null, "status": "completed" }
]
}
]
Two fields in there are easy to miss. The objective's description travels with it, so whatever your team typed into the description box is part of what the model reads, not just something a manager can look up later. And progress_percent is a real field on every key result, but the 15Five sync never fills it in: the sync reads each key result's id, name, status and target only, so it reaches the model as null unless someone has set a number on that key result inside PerfCopilot.
Four rules in the prompt decide what the draft may do with that block, and together they are the whole argument for connecting 15Five rather than summarising it by hand:
- Only a competency that weights goals may draw on them. Each skill in your review framework lists the sources it reads and how heavily, so goal data informs the sections where goal attainment is genuinely the evidence, not every paragraph.
- Each claim carries its source in brackets. A sentence drawn from this block is written as a claim followed by a bracketed source tag, the same convention as
[Source: GitHub], and that tag survives into the manager's view of the draft and into the sealed PDF. The tag names the source, not the individual objective: it marks a line as drawn from the goals synced out of 15Five rather than from a manager's memory, and it does not record which of those objectives the sentence came from. - Inventing data is forbidden, and missing data is named. When a competency weights goals and no goals arrived, the draft is instructed to say that data is pending for that source rather than filling the gap with adjectives. A visible hole is better than a confident guess.
- Attainment is evidence, not the rating. Goal status is one weighted input among the sources your framework lists, and the finished draft is screened for bias patterns before a manager sees it. An objective marked off track is a fact to discuss, not an automatic score.
The practical difference is small in a sentence and large in a review conversation: a line about goal progress is marked as coming from the objectives the employee set in 15Five, and those objectives are sitting in the tool they already use, open to be read and argued with. Tying a particular sentence to a particular objective is still a question for the conversation, because the tag names the source and carries no objective's identity with it.
Goal attainment across the team, with the source named
Once goals are in, the cycle has an attainment view: how many objectives across the team or department sit in each of the four statuses, with a drill-down list giving the employee, the objective's title, its status, and the source it came from.
That last column is the honest part, and it is there on purpose. A goal synced from 15Five and a goal typed into PerfCopilot by a manager are not the same quality of evidence, and a calibration meeting that cannot tell them apart will treat a tidy record as a strong performance. Naming the source makes that visible rather than tidy. If calibration is where your ratings actually get decided, the calibration meeting guide is the companion to this.
Where this is honest about its limits
- Objectives only. This integration reads objectives and their key results. 15Five's weekly check-ins, one-to-ones, engagement surveys and Best-Self review content are not read at all. If weekly check-in reflections are the evidence you want in a draft, this connection does not carry them.
- One page per employee. The sync asks for a single page of up to 200 objectives per person and flags the result as truncated rather than pretending it read everything beyond that.
- Everybody needs a matched 15Five account. Because the query filters strictly by owner, an employee with no matched 15Five user syncs nothing at all, and the request comes back asking you to match them first. That is deliberate: an empty goals section is visible to a manager, a silently halved one is not.
- We store objective descriptions, up to 1,000 characters, managers can read them, and they go to the model. The description text is part of the goal data PerfCopilot sends to Claude when it drafts, not just a field sitting in PerfCopilot's database. Key result targets are stored as text and shown next to each status. If your objectives carry commentary you would not want a manager reading or a draft written from, that is worth knowing before you connect.
- The status mapping is ours. We collapse 15Five's documented states into four, as set out above, and the unrecognised case reads as on track. It is a judgement, not a measurement.
- A writing layer, not a system of record. Your objectives stay in 15Five and PerfCopilot never writes to them. The finished review leaves as a sealed PDF you file wherever your records already live, so there is nothing to migrate and nothing to migrate back out of.
Where 15Five ends and a cited draft begins
| Held in 15Five | What PerfCopilot does with it | |
|---|---|---|
| Objectives and key results | the system of record | read-only, per employee, per cycle |
| The status of each objective | set by your team | mapped to one of four review statuses |
| The goal period | set by your team | matched against the cycle by overlap |
| The review prose | a cycle and a form to fill in | drafted, with each goal claim tagged to the source it came from |
| Bias screen on the drafted text | n/a | runs on every draft before you send it |
| Cost | varies by module, see 15five.com/pricing | see our pricing, no seat minimum |
The row that earns the connection is the fourth one. Keeping objectives up to date and writing a defensible review from them are different jobs, and the second is the one that eats a manager's week. For the platform-level comparison, including where 15Five is the better tool, read PerfCopilot vs 15Five; if you are weighing leaving instead of layering, 15Five alternatives is the honest version of that question.
Pair 15Five objectives with the work that produced them
An objective says what someone was aiming at. It does not say what they built on the way there, which is why a goals-only review reads thin. The same cycle gets sharper when the objective sits next to the artefacts:
- GitHub pull requests and reviews for the shipped work behind an engineering objective.
- Jira tickets and cycle time for delivery against a roadmap commitment.
- Asana projects and tasks for marketing, operations and cross-functional goals.
For the wider picture, the performance review software buyer's guide covers where a writing layer sits next to a full HR platform, the engineering performance review template shows what a cited section looks like on the page, and reducing bias in performance reviews explains what the screen on every draft is looking for.
Setting it up
- In 15Five, open your avatar menu, then Account and API. Generate a token with the
read:goalsscope and copy it, because 15Five shows it once. - In PerfCopilot, open Admin and then Integrations, find the 15Five card, paste the token and save. Leave API Base URL (optional) empty unless your tenant sits on another host:
https://my.15five.com/api/publicappears there as a greyed-out example rather than a filled-in value, and the sync falls back to exactly that address when the field is left blank. Press Test to check the credential against 15Five before anything syncs. - Match each employee to their numeric 15Five user id in the unmapped-employees list. It is the same id 15Five uses in the objective's owner field, which is why a mismatch shows up as zero objectives rather than as an error.
- Sync an employee's goals, then generate the review for the active cycle and read which lines carry a goals source tag. The credential walkthrough is in the 15Five setup docs, and the field-by-field mapping, including the status table and the troubleshooting notes, is in the 15Five goals docs.
Prefer to see the output before connecting anything? Run the performance review generator or the standalone bias checker first, and read how connected sources are stored and retained on the security page.
FAQ
What does PerfCopilot read from 15Five? Objectives owned by each matched employee, and the key results nested inside them. From each objective it reads the name, description, status and period dates; from each key result the name, target and status. It is a read-only API token with the goals scope, one endpoint, and nothing is written back into 15Five.
Does it read my weekly check-ins or Best-Self reviews? No. The sync calls the objectives endpoint and nothing else. Weekly check-ins, one-to-ones, engagement surveys and the content of 15Five review cycles are never read. If check-in reflections are the evidence you want in a draft, this integration does not provide them.
Why did my objectives sync as empty? Almost always an unmatched employee. The query filters strictly by the 15Five owner id, so a person with no matched 15Five user returns nothing and the request asks you to match them first. Match the numeric id from your 15Five user list and sync again.
Will the review just score people on goal attainment? No. Goal status is one weighted source among those your competency framework lists, and only the competencies that weight goals draw on it. The draft is told to tag each claim with the source it was drawn from, never to invent data, and to say that data is pending when a weighted source is empty. A bias and fairness screen then runs before a manager sees the draft.
Do I have to move my team off 15Five? No. PerfCopilot is a review-writing layer rather than a platform migration. Your objectives stay in 15Five, PerfCopilot never writes to them, and the finished review leaves as a sealed PDF you file wherever your records already live. There is no seat minimum, so one manager can run it for one team.
Connect 15Five and draft a review → · read-only, no credit card, no seat minimum
Frequently asked questions
- What does PerfCopilot read from 15Five?
- Objectives owned by each matched employee, and the key results nested inside them. From each objective it reads the name, description, status and period dates; from each key result the name, target and status. It is a read-only API token with the goals scope, one endpoint, and nothing is written back into 15Five.
- Does it read my weekly check-ins or Best-Self reviews?
- No. The sync calls the objectives endpoint and nothing else. Weekly check-ins, one-to-ones, engagement surveys and the content of 15Five review cycles are never read. If check-in reflections are the evidence you want in a draft, this integration does not provide them.
- Why did my objectives sync as empty?
- Almost always an unmatched employee. The query filters strictly by the 15Five owner id, so a person with no matched 15Five user returns nothing and the request asks you to match them first. Match the numeric id from your 15Five user list and sync again.
- Will the review just score people on goal attainment?
- No. Goal status is one weighted source among those your competency framework lists, and only the competencies that weight goals draw on it. The draft is told to tag each claim with the source it was drawn from, never to invent data, and to say that data is pending when a weighted source is empty. A bias and fairness screen then runs before a manager sees the draft.
- Do I have to move my team off 15Five?
- No. PerfCopilot is a review-writing layer rather than a platform migration. Your objectives stay in 15Five, PerfCopilot never writes to them, and the finished review leaves as a sealed PDF you file wherever your records already live. There is no seat minimum, so one manager can run it for one team.