Ask a human expert
When the knowledge base doesn’t have an answer, ask a person. Halyard routes the question to the right expert in Slack and returns their reply as new evidence for the agent. The agent then searches for relevant organizational knowledge and writes one normal, cited answer rather than forwarding the human reply as the final response. Ask only after a real search miss — not as a first move.
This page is a rule you write for your agent. For how routing picks a person, see Experts & routing.
When to ask, when not to
Section titled “When to ask, when not to”Ask a human when:
- A focused
search_knowledge(with the retry-with-fewer-filters habit) genuinely returned nothing. - The decision is judgment, preference, or undocumented context a human holds.
Don’t ask when:
- The answer is in the codebase, the docs, or a knowledge entry you haven’t searched for yet.
- You’re asking to confirm something you can verify yourself.
The sequence
Section titled “The sequence”-
See who’s available.
list_teamshows experts, their roles, and skills so you can target the question.list_team(role?, skill?, available_only?){"members": [{"name": "David Kim","roles": ["engineer"],"skills": ["React", "TypeScript", "Accessibility"],"availability": "ONLINE"},{"name": "James Okonkwo","roles": ["architect", "engineer"],"skills": ["System Design", "Cloud Architecture", "Security"],"availability": "ONLINE"}]}Roles are stored lowercase (
engineer,pm,architect); skills are Title-Case domains (React,System Design). Filter byroleto ask a category,skillto ask a specialist. -
Ask.
ask_expertsends the question. Target it withroleorskillso it reaches the right person; let Halyard pick the individual.ask_expert(prompt, role?, skill?, force_human?, options?, conversation_id?)ask_expert(prompt: "We're choosing between per-user OAuth and domain-wide sync for calendar import. Which did we land on, and why?",skill: "System Design") -
Handle the return.
ask_expertreturns a discriminated union — branch on it:- Resolved from the knowledge base. Halyard checked the KB first and the question had an answer. You get the answer back immediately and no human was interrupted. Use it; you’re done. (Pass
force_human: trueonly when you specifically need a person despite a KB match.) - Pending a human. No KB answer, so it routed to Slack. You get a
conversation_idand apendingstatus. Move to step 4.
- Resolved from the knowledge base. Halyard checked the KB first and the question had an answer. You get the answer back immediately and no human was interrupted. Use it; you’re done. (Pass
-
Get the reply. Use
check_responsewith theconversation_id. Passwait: trueto block for the reply instead of polling.check_response(conversation_id, wait?)check_response(conversation_id: "…", wait: true) -
Synthesize the answer. Treat the returned human reply as evidence, not ready-to-forward copy. Search the knowledge base for relevant supporting or conflicting information, then answer in the normal assistant voice. Attribute the human reply by expert name as one source, cite relevant knowledge entries, and surface disagreements rather than hiding them. Slack-originated asks perform this resumed agent turn automatically; MCP hosts resume when the tool returns and must follow the same rule.
-
Follow up if needed. Send more context or a clarifying question into the same thread with
reply_to_expert.reply_to_expert(conversation_id, message)The wait begins after the follow-up message, so an older expert reply cannot satisfy it. If a new reply arrives, treat it as evidence and repeat the search-and-synthesize step above.
-
Capture the answer. When the reply changes what you do, file it with
summarize_conversationso it becomes searchable knowledge. This step is not optional — see Capture what you learn.summarize_conversation(conversation_id, question, answer, source_url?, source_provider?)
The agent rule
Section titled “The agent rule”Ask a human only after a genuine search_knowledge miss.
1. list_team(role|skill) to see who can answer; target the question.2. ask_expert(prompt, role|skill). Branch on the return: - Resolved from the knowledge base -> use the answer, you're done. - Pending a human -> you get a conversation_id; continue.3. check_response(conversation_id, wait: true). The wait returns in <=55s; if still pending, do other work and poll again later. Never tight-loop.4. On a human reply, search_knowledge for relevant context. Synthesize one normal answer that attributes the expert response, cites relevant entries, and surfaces conflicts.5. reply_to_expert(conversation_id, message) to add context or clarify.6. When the answer changes what you do, summarize_conversation(conversation_id, question, answer) so the next agent finds it. Always capture.In practice
Section titled “In practice”- Search before you ask — the step that comes first.
- Capture what you learn — turning the answer into reusable knowledge.
- Experts & routing — how roles, skills, and availability decide who’s asked.
- Tool reference — full signatures.