> Source: https://wexa.ai/docs/connectors/list-skills

# list-skills

List this project's existing, already-usable skills, one item per skill. It is the only way to discover which skills you can attach to an agent. Needs the `fabric:orchestrate.read` grant.

**List a connector's skills**

**Wexa MCP server**

```bash
curl -sS -X POST https://fabric.wexa.ai/mcp/$FABRIC_PROJECT_ID \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "Mcp-Session-Id: $MCP_SESSION_ID" \
  -H "content-type: application/json" -H "accept: application/json" \
  -d '{"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"list-skills","arguments":{"category":"duckduckgo"}}}'
```

```json
{
  "content": [
    {
      "type": "text",
      "text": "{\"lifecycle_id\":\"qlc_000016\",\"result\":{\"skills\":[{\"action\":\"Search\",\"connector\":\"Duckduckgo\",\"description\":\"Search DuckDuckGo Instant Answer API and return abstract and related topics.\",\"skill_id\":\"6ac7300653328ca8315f0308\"}],\"total_count\":1}}"
    }
  ],
  "isError": false
}
```

**REST API**

```bash
curl -sS https://fabric.wexa.ai/v1/list-skills \
  -H "authorization: Bearer $FABRIC_API_KEY" \
  -H "content-type: application/json" \
  -d '{"category":"duckduckgo"}'
```

```json
{
  "lifecycle_id": "qlc_000016",
  "result": {
    "skills": [
      {
        "action": "Search",
        "connector": "Duckduckgo",
        "description": "Search DuckDuckGo Instant Answer API and return abstract and related topics.",
        "skill_id": "6ac7300653328ca8315f0308"
      }
    ],
    "total_count": 1
  }
}
```

**TypeScript SDK**

```ts
import { Fabric } from '@wexa-fabric/sdk'

const fabric = new Fabric()
const result = await fabric.listSkills({ category: 'duckduckgo' })
```

```ts
// result is the payload itself, with no `.result` to read
{
  skills: [
    {
      action: 'Search',
      connector: 'Duckduckgo',
      description: 'Search DuckDuckGo Instant Answer API and return abstract and related topics.',
      skill_id: '6ac7300653328ca8315f0308'
    }
  ],
  total_count: 1
}
```

**Python SDK**

```python
from wexa import Fabric

fabric = Fabric()
out = fabric.list_skills(category="duckduckgo")
```

```python
# out is the result, already unwrapped
{
    "skills": [
        {
            "action": "Search",
            "connector": "Duckduckgo",
            "description": "Search DuckDuckGo Instant Answer API and return abstract and related topics.",
            "skill_id": "6ac7300653328ca8315f0308"
        }
    ],
    "total_count": 1
}
```

## Parameters

Every parameter is optional: a bare call works.

| Parameter | Type | Required | Notes |
| --- | --- | --- | --- |
| `category` | string | Optional | Restrict to one connector's skills, such as `linear`. Matched case-insensitively against the connector name or its actions' category. |
| `limit` | integer | Optional | Most connectors whose skills are returned. Default 100. Must be a positive integer. |
| `search_key` | string | Optional | Free-text filter on skill or connector name or description. |

**Show full response**

A real response, captured from a live call to `list-skills` with `category: "duckduckgo"`, after `provision-connector` connected DuckDuckGo:

**Result of list-skills**

**REST API**

```json
{
  "lifecycle_id": "qlc_000016",
  "result": {
    "skills": [
      {
        "action": "Search",
        "connector": "Duckduckgo",
        "description": "Search DuckDuckGo Instant Answer API and return abstract and related topics.",
        "skill_id": "6ac7300653328ca8315f0308"
      }
    ],
    "total_count": 1
  }
}
```

**Wexa MCP server**

```json
{
  "content": [
    {
      "type": "text",
      "text": "{\"lifecycle_id\":\"qlc_000016\",\"result\":{\"skills\":[{\"action\":\"Search\",\"connector\":\"Duckduckgo\",\"description\":\"Search DuckDuckGo Instant Answer API and return abstract and related topics.\",\"skill_id\":\"6ac7300653328ca8315f0308\"}],\"total_count\":1}}"
    }
  ],
  "isError": false
}
```

**TypeScript SDK**

```ts
// the object you get back IS the result — there is no `.result` to read
{
  skills: [
    {
      action: 'Search',
      connector: 'Duckduckgo',
      description: 'Search DuckDuckGo Instant Answer API and return abstract and related topics.',
      skill_id: '6ac7300653328ca8315f0308'
    }
  ],
  total_count: 1
}

// The TS SDK names these camelCase — lifecycleId, traceId — where Python uses
// lifecycle_id and trace_id. Both are non-enumerable: readable, but omitted by
// Object.keys() and JSON.stringify(). `result.lifecycleId` here is undefined.
result.lifecycleId // 'qlc_000016'
```

**Python SDK**

```python
# a dict subclass; `result` is already unwrapped
{
 "skills": [
  {
   "action": "Search",
   "connector": "Duckduckgo",
   "description": "Search DuckDuckGo Instant Answer API and return abstract and related topics.",
   "skill_id": "6ac7300653328ca8315f0308"
  }
 ],
 "total_count": 1
}

out.lifecycle_id  # 'qlc_000016' — an attribute, not a key
```

Each item is one skill. `skill_id` is the id an agent accepts; `connector` and `action` are the
connector's name and the action the skill runs. When no connector is connected, `skills` is empty
and a `note` says no connector is connected yet, not that none exist.

**More details**

A skill appears only if its connector is provisioned in this project, because provisioning a connector creates one skill per real action. If the skill you need is not returned, that connector is not provisioned yet: try [`provision-connector`](/docs/connectors/provision-connector), which provisions credential-free connectors and creates their skills. A connector that needs an API key or OAuth still needs a person in the console. Never invent a skill id or attach a placeholder: an un-backed skill silently does nothing when the flow runs.

Pass a `skill_id` to an agent as it is: in `skill_ids` for `create-agent` or `update-agent`, or in an agent's `skills[]` in a `create-process-flow` manifest or `update-process-flow`.

For example:

**Use a skill_id from list-skills**

**TypeScript SDK**

```ts
const { skills } = await fabric.listSkills({ category: 'duckduckgo' })

await fabric.createAgent({
  name: 'Web researcher',
  role: 'Task',
  skill_ids: [skills[0].skill_id],
})
```

**Python SDK**

```python
skills = fabric.list_skills(category="duckduckgo")["skills"]

fabric.create_agent(
    name="Web researcher",
    role="Task",
    skill_ids=[skills[0]["skill_id"]],
)
```

Not marked consequential: it only reads, so it is audited lightly and never held for approval. For when and how to use skills, see [Skills, actions and triggers](/docs/automation/overview).

Every tool call works the same way: [How every tool call works](/docs/sdks-and-apis/how-every-tool-call-works).
