Skip to main content
Writes to your heyBTW workspace. It appends observations about people on one of your own collabs. It writes no attendance status, RSVP, task, List or CRM record, and it sends nothing.
The marketer’s question is “how do I keep what the team learned at the event?” Reach for this tool when the user debriefs person by person (“Marcus met Priya, she wants a security review in Q1”, “Dana never came”), when you find a follow-up in the user’s own CRM, or when an invite or a nudge you sent needs a record. Follows the heyBTW MCP rules.

When to use it

  • “Marcus met Priya at the dinner. She is evaluating in Q1.”
  • “Dana never actually showed up, even though Luma says checked in.”
  • “I emailed Theo the deck on Tuesday, log it.”
  • “I sent Jane a personal invite on LinkedIn yesterday.”
  • After you sent a nudge to an owner through the user’s chat or mail connector, with the message id it returned.

Parameters

Each item has person (the email this workspace holds for them) and any of these kinds. One item can carry several kinds; each becomes its own fact. Every at is RFC 3339 with its offset, for example 2026-10-13T09:30:00-05:00. An at later than now is refused.

Workflow

1

Resolve the collab

Take channel_id from list_events. If the user named the event, event_name works, but an ambiguous name records nothing and lists the candidates.
2

Check each person is in the workspace

person must be an email this workspace holds. A person heyBTW has no record of is rejected; add them first with import_people.
3

Build one item per person

Put only facts the user stated or you saw. A second follow-up or invite for the same person is another item.
4

Generate a client_request_id and call once

On a transport error, retry with the SAME client_request_id. A committed call comes back with idempotent_replay: true and is never repeated. Reusing the id for different observations is refused.
5

Report recorded and rejected

Say how many facts were recorded and name each rejected reference with its reason.

Response

The success shape below is from the code (tools/record_observation.py and observation-contract.json), not a live call: this page was written against a production workspace, so nothing was recorded. data[0] holds: Keep each observation_id: save_task takes it as observation_ref when a follow-up comes out of the debrief. Read observations back with get_event_details (include_contacts), where notes, follow-up summaries and nudge proofs appear on the contact rows. A partner of the collab never sees them. The validation error below is a real response, trimmed, from a call that sent a channel_id and no observations:

Rules the agent must follow

  • An invite is never an RSVP and never a touch. It never changes attendance, a registration or a funnel count. Record one only for a send that happened or that the user states, never from a draft or from list membership.
  • Never record again an invite that activate_list sent, or a List the user sent outside heyBTW that was recorded with activate_list destination_type: "external". activate_list already logs each of those invites.
  • A nudge is never a touch. It is your ask going out to the person’s owner, recorded as nudged, never as followed_up, and only with the message_ref the connector returned. Without that proof it is a draft: record nothing.
  • followed_up records what the CRM shows, not proof of contact: an outbound email, call, meeting held, note or sequence step you saw, or one the user stated. Never an inbound reply, never inferred from a completed task or a sent invite. When a CRM is connected in heyBTW, its own read stays the source for follow-up status.
  • attended_confirmed sits beside the platform’s attendance and never overwrites it. Only CHECKED_IN on the platform is attended.
  • Observations are append-only: a later one adds, never replaces.

Errors and gaps