Conversation Skills are the discrete, callable actions a tenant’s chatbot can perform on behalf of a contact. Each service registers its skills with the Communications service, which routes incoming WhatsApp or email messages to the appropriate skill based on the active conversation menu, flow, or training phrases.
Skills are addressed by a fully-qualified name in the form <service>.<skill_name> (e.g. finance.ar_balance). The active set of skills available to a tenant depends on which Portal modules are enabled.
graph LR
USER[Contact via WhatsApp / Email] --> COMM[Communications dispatcher]
COMM --> AUTH{Verify caller}
AUTH -->|unverified| FLOW[Lead-capture flow]
AUTH -->|phone_matched / contact_confirmed| SKILL[Invoke skill endpoint]
SKILL --> SVC[Service handler]
SVC --> RESP[Formatted reply]
RESP --> USER
- A contact sends a message on WhatsApp or email.
- The dispatcher resolves the caller to a Business Partner or Prospect.
- Based on the active Conversation Menu or Conversation Flow, a skill is selected.
- The dispatcher invokes the skill’s internal endpoint on the owning service.
- The service returns a localized response that is sent back to the contact.
The Conversation Menu Builder and Conversation Flows pages (under Communications) let tenants choose which skills are surfaced and in what order.
Skills declare the minimum verification level a caller must have to invoke them.
| Level | Meaning | Typical use |
|---|
| Unverified | The caller is anonymous; the system has no Business Partner or Contact match. | Lead-capture skills (create a prospect, create an opening deal). |
| Phone Matched | The caller’s phone number maps to a known Business Partner. | Skills that act on the matched BP without requiring identity confirmation. |
| Contact Confirmed | The caller has identified themselves and the contact identity is confirmed against the BP. | Default for self-service reads (balance, invoices, tickets). |
All user-facing skills support WhatsApp and email unless noted otherwise. Internal skills are invoked only by the dispatcher and are never exposed directly to a contact.
| Skill | Description | Parameters | Verification | Menu |
|---|
bp.resolve_by_phone | Resolves a WhatsApp/email caller phone to a BP and contact. Internal. | phone | Phone Matched | — |
bp.resolve_by_name | Resolves a free-text company name to a BP ID. Internal. | name (≥ 3 chars) | Phone Matched | — |
bp.account_summary | Compact account snapshot — name, status, balances, primary contact, industry. | bp_id, language | Contact Confirmed | Yes |
| Skill | Description | Parameters | Verification | Menu |
|---|
finance.ar_balance | Open A/R balance with an aging breakdown (current, 1-30, 31-60, 61-90, 90+ days). | bp_id, language | Contact Confirmed | Yes |
finance.invoice_list_open | Lists up to 5 of the most recent open A/R invoices for the caller’s BP. | bp_id, language, limit (1-10) | Contact Confirmed | Yes |
| Skill | Description | Parameters | Verification | Menu |
|---|
commerce.quotation_list_recent | Lists up to 5 recent Sales Quotations — number, amount, status, date. | bp_id, language, limit (1-10) | Contact Confirmed | Yes |
| Skill | Description | Parameters | Verification | Menu |
|---|
items.search | Free-text item search via the universal search index. | query, language | Contact Confirmed | Yes |
items.stock_check | Lookup an item by code or name and return the on-hand stock total. | query, language | Contact Confirmed | Yes |
items.find_by_code | Exact-match item lookup by item_code (case-insensitive). | code, language | Contact Confirmed | Yes |
| Skill | Description | Parameters | Verification | Menu |
|---|
crm.create_deal | Create a CRM deal for a BP or prospect. Stored with an optional product tag. Internal — invoked from lead-capture flows. | bp_id, title, product?, amount (≥ 0), currency (default USD) | Unverified | — |
| Skill | Description | Parameters | Verification | Menu |
|---|
prospects.create_or_find | Find a prospect by phone, or create a new prospect when no match exists. Returns the prospect_id. Internal — invoked from lead-capture flows. | name, phone, email?, company? | Unverified | — |
| Skill | Description | Parameters | Verification | Menu |
|---|
projects.status_summary | Portfolio overview of the caller’s active projects. | bp_id?, since?, language (es / en), open_task_limit? | Contact Confirmed | Yes |
| Skill | Description | Parameters | Verification | Channel | Menu |
|---|
support.create_ticket | Create a service-desk ticket from WhatsApp. The orchestrator pre-fills bp_id. | subject, description, priority (low / normal / high / urgent), bp_id | Phone Matched | WhatsApp only | — |
support.get_ticket_status | Status, priority and last-update for a single ticket by number (e.g. SD-00012). | ticket_number | Contact Confirmed | All | — |
support.list_my_tickets | Caller’s last 5 tickets, ordered by most recent update. The orchestrator pre-fills bp_id. | bp_id | Contact Confirmed | All | — |
Phase 1 skills declare an empty required_permissions list. Authorization is enforced through tenant scoping (a skill can only see data inside the caller’s tenant) and BP scoping (read skills are limited to the caller’s matched Business Partner). Role-based permission gating is reserved for future skills that perform write actions outside the caller’s own scope.
- Each service registers its skills at startup with the Core backend. Communications fetches the active registry per tenant.
- A skill’s endpoint path is validated against an allowlist of the form
/api/internal/<service>/skills/<name>.
- When a skill is retired or a tenant disables a module, Core publishes a
core.chat_skills.changed event and Communications refreshes its cache.
- The dispatcher re-validates skill availability at invocation time, so a stale menu entry cannot reach a retired skill.
- Skill responses are always localized based on the
language parameter, which the dispatcher derives from the contact’s preferred language.
- Menu-surfaced skills are ordered by the menu position declared at registration. Tenants can reorder, hide or relabel them through the Conversation Menu Builder.
- Internal skills (verification level
Unverified with no menu position) are never selectable from a menu — they are invoked programmatically by a flow.