Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
# Freshservice API v2 reference
|
|
|
|
|
|
|
|
|
|
|
|
Base URL: `https://<domain>.freshservice.com/api/v2`. Auth is HTTP Basic with the
|
|
|
|
|
|
API key as username (handled by `scripts/fs.py`). Full docs: https://api.freshservice.com
|
|
|
|
|
|
|
|
|
|
|
|
## Codes
|
|
|
|
|
|
|
2026-06-16 21:36:25 -06:00
|
|
|
|
**Ticket status (defaults):** 2 Open · 3 Pending · 4 Resolved · 5 Closed
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
**Ticket priority:** 1 Low · 2 Medium · 3 High · 4 Urgent
|
2026-06-16 21:36:25 -06:00
|
|
|
|
|
|
|
|
|
|
> ⚠️ Instances often define **custom statuses** beyond the 4 defaults (e.g.
|
|
|
|
|
|
> "Working", "Scheduled", "Waiting Vendor Support"). Resolved and Closed are
|
|
|
|
|
|
> always ids **4** and **5**; every other status is "open". To list them all,
|
|
|
|
|
|
> read the `status` field choices:
|
|
|
|
|
|
> `GET /ticket_form_fields` → field where `name == "status"` → `choices[]`.
|
|
|
|
|
|
> So "all my tickets that aren't resolved/closed" must enumerate *every*
|
|
|
|
|
|
> non-4/5 status, not just `(status:2 OR status:3)`. Recipe:
|
|
|
|
|
|
> `agent_id:<id> AND (status:2 OR status:3 OR status:6 OR status:7 OR ...)`
|
|
|
|
|
|
> using all open ids from the status field.
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
**Ticket source:** 1 Email · 2 Portal · 3 Phone · 4 Chat · 5 Feedback widget ·
|
|
|
|
|
|
6 Yammer · 7 AWS CloudWatch · 8 PagerDuty · 9 Walkup · 10 Slack
|
|
|
|
|
|
|
|
|
|
|
|
Status/priority for changes use their own workflow codes; list a few existing
|
|
|
|
|
|
records to infer them, or read the ticket-fields / change-fields endpoints.
|
|
|
|
|
|
|
|
|
|
|
|
## Endpoints
|
|
|
|
|
|
|
|
|
|
|
|
| Resource | List | Create | View | Update | Delete |
|
|
|
|
|
|
|----------|------|--------|------|--------|--------|
|
|
|
|
|
|
| Tickets | `GET /tickets` | `POST /tickets` | `GET /tickets/{id}` | `PUT /tickets/{id}` | `DELETE /tickets/{id}` |
|
|
|
|
|
|
| Ticket filter | `GET /tickets/filter?query="..."` | — | — | — | — |
|
|
|
|
|
|
| Conversations | `GET /tickets/{id}/conversations` | reply: `POST /tickets/{id}/reply`; note: `POST /tickets/{id}/notes` | — | `PUT /conversations/{id}` | `DELETE /conversations/{id}` |
|
|
|
|
|
|
| Assets | `GET /assets` | `POST /assets` | `GET /assets/{display_id}` | `PUT /assets/{display_id}` | `DELETE /assets/{display_id}` |
|
|
|
|
|
|
| Agents | `GET /agents` | `POST /agents` | `GET /agents/{id}` | `PUT /agents/{id}` | — |
|
|
|
|
|
|
| Requesters | `GET /requesters` | `POST /requesters` | `GET /requesters/{id}` | `PUT /requesters/{id}` | — |
|
|
|
|
|
|
| Groups | `GET /groups` | `POST /groups` | `GET /groups/{id}` | `PUT /groups/{id}` | `DELETE /groups/{id}` |
|
|
|
|
|
|
| Departments | `GET /departments` | `POST /departments` | `GET /departments/{id}` | `PUT /departments/{id}` | `DELETE /departments/{id}` |
|
|
|
|
|
|
| Changes | `GET /changes` (+ `/changes/filter`) | `POST /changes` | `GET /changes/{id}` | `PUT /changes/{id}` | `DELETE /changes/{id}` |
|
|
|
|
|
|
| Problems | `GET /problems` | `POST /problems` | `GET /problems/{id}` | `PUT /problems/{id}` | `DELETE /problems/{id}` |
|
|
|
|
|
|
| Releases | `GET /releases` | `POST /releases` | `GET /releases/{id}` | `PUT /releases/{id}` | `DELETE /releases/{id}` |
|
|
|
|
|
|
| Current agent | `GET /agents/me` | — | — | — | — |
|
|
|
|
|
|
|
|
|
|
|
|
Other useful endpoints reachable the same way: `/solutions/categories`,
|
|
|
|
|
|
`/solutions/folders`, `/solutions/articles`, `/products`, `/vendors`,
|
|
|
|
|
|
`/ticket_fields`, `/tickets/{id}/time_entries`, `/canned_responses`.
|
|
|
|
|
|
|
|
|
|
|
|
## Ticket fields (create/update)
|
|
|
|
|
|
|
|
|
|
|
|
`subject`, `description` (HTML ok), `email` or `requester_id`, `priority`,
|
|
|
|
|
|
`status`, `source`, `group_id`, `responder_id` (assigned agent), `type`
|
|
|
|
|
|
(e.g. "Incident", "Service Request"), `tags` (array), `category`,
|
|
|
|
|
|
`sub_category`, `custom_fields` (object), `due_by`, `fr_due_by`.
|
|
|
|
|
|
|
|
|
|
|
|
Provide **either** `email` **or** `requester_id`. For a public reply the
|
|
|
|
|
|
requester is emailed; a note with `"private": true` is internal-only.
|
|
|
|
|
|
|
|
|
|
|
|
## Filter (query) syntax — /tickets/filter and /changes/filter
|
|
|
|
|
|
|
|
|
|
|
|
- Format: `field:value`, combined with `AND` / `OR`.
|
|
|
|
|
|
- Strings single-quoted: `tag:'vip'`. Numbers/dates bare or quoted.
|
|
|
|
|
|
- Operators on dates/numbers: `>`, `<`, e.g. `created_at:>'2026-01-01'`.
|
|
|
|
|
|
- Filterable ticket fields include: `status`, `priority`, `agent_id`,
|
|
|
|
|
|
`group_id`, `requester_id`, `type`, `source`, `tag`, `created_at`,
|
|
|
|
|
|
`updated_at`, `due_by`, plus custom fields by name.
|
|
|
|
|
|
- The whole expression must be URL-double-quoted; `scripts/fs.py` does this when
|
|
|
|
|
|
you pass `--param query=...` / `--param filter=...`.
|
|
|
|
|
|
|
2026-06-16 21:28:36 -06:00
|
|
|
|
Two common gotchas:
|
|
|
|
|
|
- **Assignee is `agent_id` (numeric), not an email.** Resolve an email to an id
|
|
|
|
|
|
first: `GET /agents?email=person@co.com` → read `id`, then filter on it.
|
|
|
|
|
|
- **No "not" operator for status.** "Open / unresolved / not closed" must be
|
|
|
|
|
|
enumerated: `(status:2 OR status:3)`. Parenthesize the OR group when AND-ing it.
|
|
|
|
|
|
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
Examples:
|
|
|
|
|
|
- `status:2 AND priority:3`
|
|
|
|
|
|
- `agent_id:0 AND status:2` — unassigned open tickets
|
2026-06-16 21:28:36 -06:00
|
|
|
|
- `agent_id:21000816864 AND (status:2 OR status:3)` — assigned to an agent, still open
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
- `type:'Incident' AND created_at:>'2026-06-01'`
|
|
|
|
|
|
|
2026-06-16 21:28:36 -06:00
|
|
|
|
Multi-workspace accounts: `/tickets/filter` searches one workspace by default.
|
|
|
|
|
|
Pass `--param workspace_id=<id>` to target another (an agent's `workspace_ids`
|
|
|
|
|
|
lists which ones they're in).
|
|
|
|
|
|
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
## Listing vs. filtering
|
|
|
|
|
|
|
|
|
|
|
|
- `GET /tickets` supports `filter` presets (`new_and_my_open`, `watching`,
|
|
|
|
|
|
`spam`, `deleted`), `updated_since`, `order_by`, `order_type`, `page`,
|
|
|
|
|
|
`per_page` (max 100), and `include` (`conversations`, `requester`, `stats`).
|
2026-08-24 15:37:16 -06:00
|
|
|
|
- `GET /tickets/{id}?include=assets` is the **only** way to see a ticket's
|
|
|
|
|
|
associated CMDB assets — they come back embedded in the ticket object. There
|
|
|
|
|
|
is no `/tickets/{id}/associated-assets` endpoint (it 404s). Other
|
|
|
|
|
|
single-ticket includes: `conversations`, `requester`, `requested_for`,
|
|
|
|
|
|
`stats`, `problem`, `tags`, `related_tickets`.
|
Freshservice skill for Claude: tickets, assets, people, changes/problems/releases
Stdlib-only fs.py helper wrapping the Freshservice REST API v2 (auth, URL
building, filter quoting, pagination, error surfacing), plus SKILL.md and a
reference of endpoints, status/priority codes, and filter-query syntax.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-16 18:14:13 -06:00
|
|
|
|
- `GET /tickets/filter?query="..."` is for ad-hoc field queries (also 100/page).
|
|
|
|
|
|
|
|
|
|
|
|
## Pagination & rate limits
|
|
|
|
|
|
|
|
|
|
|
|
- 30 results/page default, 100 max via `per_page`. `scripts/fs.py` surfaces
|
|
|
|
|
|
`next_page` when a next-page Link header is present.
|
|
|
|
|
|
- Per-plan minute limits (100–500/min). Responses include
|
|
|
|
|
|
`rate_limit_remaining`.
|