Skip to main content
Glama

Fetch Post Engagers

fetch_post_engagers

Visibility follows the user's LinkedIn account: any post it can view works, and private or deleted posts return a plain error. The list is capped at 500 reactions + 500 comments per post; on a bigger post the return flags the cut-off. Data fetched within the last 6 hours is served from the database at no cost; a real fetch counts one action against the shared daily engagement-fetch budget and paces its LinkedIn requests, so a post with hundreds of engagers takes around half a minute — set that expectation with the user before calling this on a big post.

When this runs in an agent, every engager is materialized as a reviewable agent_search_results row (entity_type='person', data carries headline, reaction_value, comment_text, provider_id, source_post_url), rendered in the agent's Output tab and queryable via query_search_results. Re-running updates existing rows rather than duplicating them. Pass list_name to name their list; absent, they land in the 'default' list. By default the full unfiltered list materializes — to act on only a subset (ICP fit, founders only, a specific role), qualify the stored rows first (headline triage via query_linkedin_post_engagements) and queue outreach on just the keepers.

After this returns, filter and slice the full list with query_linkedin_post_engagements using post_id = <post_analytics_id>, then queue outreach with one batched setup_linkedin_sequence call passing each person's provider_id. Send-time resolution skips anyone already connected, so they don't need pre-filtering here. On success, a dict {'success': True, 'post_analytics_id': int, 'author_name': str, 'is_own_post': bool, 'post_text_snippet': str, 'from_cache': bool, 'reactions_stored': int, 'comments_stored': int, 'unique_engagers': int, 'truncated': bool, 'budget': {'used_today': int, 'limit': int}, 'engagers_preview': [first 10 people], 'next_step': str, 'list'?: {'list_name', 'created', 'updated', 'total'}}. On failure, {'success': False, 'error': str} when the post isn't visible to the user's account, the daily budget is exhausted, or LinkedIn actions are paused after a rate limit.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
persistNoDefault True — in an agent, every engager is saved as a person row automatically (see `list_name`). Pass False only for a read-only lookup the user doesn't want on a list: the raw engagement rows still land and stay queryable via `query_linkedin_post_engagements`, but no `agent_search_results` list is written. To filter the saved engagers, record a `verdict` on them with `record_search_results` instead.
agent_idNoOptional — a specific agent to materialize the engager list into. Omit it to use the running agent, which is the usual case.
post_urlYesLinkedIn post URL (activity, ugcPost, and share forms all work) or a raw activity ID.
list_nameNoShort kebab slug naming the list bucket (e.g. 'launch-post-engagers'). Absent, engagers land in the 'default' list.

Schema Changelog

Changes observed during successful MCP inspections.

  1. Changed1 schema field changed
    • changedInput schema / properties / persist / description
      Previous value: -"Default True — in an agent, every engager is saved as a person\nrow automatically (see `list_name`). Pass False to fetch the\nengagers without saving them as person rows: the raw engagement rows\nstill land and stay queryable via `query_linkedin_post_engagements`,\nbut no `agent_search_results` list is written — for a flow that\nrecords only a filtered subset itself, so the full unfiltered list\nwouldn't also clutter the Output tab."New value: +"Default True — in an agent, every engager is saved as a person\nrow automatically (see `list_name`). Pass False only for a read-only\nlookup the user doesn't want on a list: the raw engagement rows still\nland and stay queryable via `query_linkedin_post_engagements`, but no\n`agent_search_results` list is written. To filter the saved engagers,\nrecord a `verdict` on them with `record_search_results` instead."
  2. Changed3 schema fields changed
    • addedInput schema / properties / agent_id
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "integer"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "Optional — a specific agent to materialize the engager list\ninto. Omit it to use the running agent, which is the usual case."
      +}
    • changedInput schema / properties / persist / description
      Previous value: -"Default True — in a task, every engager is saved as a person\nrow automatically (see `list_name`). Pass False to fetch the\nengagers without saving them as person rows: the raw engagement rows\nstill land and stay queryable via `query_linkedin_post_engagements`,\nbut no `agent_search_results` list is written — for a flow that\nrecords only a filtered subset itself, so the full unfiltered list\nwouldn't also clutter the Output tab."New value: +"Default True — in an agent, every engager is saved as a person\nrow automatically (see `list_name`). Pass False to fetch the\nengagers without saving them as person rows: the raw engagement rows\nstill land and stay queryable via `query_linkedin_post_engagements`,\nbut no `agent_search_results` list is written — for a flow that\nrecords only a filtered subset itself, so the full unfiltered list\nwouldn't also clutter the Output tab."
    • removedInput schema / properties / task_id
      Removed value: -{
      -  "anyOf": [
      -    {
      -      "type": "integer"
      -    },
      -    {
      -      "type": "null"
      -    }
      -  ],
      -  "default": null,
      -  "description": "Optional — a specific task to materialize the engager list\ninto. Omit it to use the running task, which is the usual case."
      -}
  3. Changed3 schema fields changed
    • changedInput schema / properties / list_name / description
      Previous value: -"Short kebab slug naming the list bucket (e.g.\n'launch-post-engagers'). Pass together with `task_id`."New value: +"Short kebab slug naming the list bucket (e.g.\n'launch-post-engagers'). Absent, engagers land in the 'default' list."
    • addedInput schema / properties / persist
      Added value: +{
      +  "default": true,
      +  "description": "Default True — in a task, every engager is saved as a person\nrow automatically (see `list_name`). Pass False to fetch the\nengagers without saving them as person rows: the raw engagement rows\nstill land and stay queryable via `query_linkedin_post_engagements`,\nbut no `agent_search_results` list is written — for a flow that\nrecords only a filtered subset itself, so the full unfiltered list\nwouldn't also clutter the Output tab.",
      +  "type": "boolean"
      +}
    • changedInput schema / properties / task_id / description
      Previous value: -"Pass together with `list_name` to materialize the full\nunfiltered engager list into this task's search results. When\nthe user wants only a subset (ICP fit, founders only, a\nspecific role), omit both — qualify via\nquery_linkedin_post_engagements first, then persist the keepers\nwith record_search_results."New value: +"Optional — a specific task to materialize the engager list\ninto. Omit it to use the running task, which is the usual case."
  4. First observed

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations only say readOnlyHint=false and destructiveHint=false, but the description discloses real behavior: visibility tied to the user's account, errors on private/deleted posts, a 500+500 cap with truncation flag, a 6-hour cache with cost implications, a shared daily budget cost, request pacing (~half a minute), and idempotent re-runs. This is exactly the context annotations cannot carry.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded summary followed by visibility, limits, budget and downstream workflow — well ordered and each section earns its place for a complex, multi-effect tool. It is on the long side, with some repetition of list_name/persist behavior already in the schema, but not wasteful enough to drop below 4.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Despite no output schema, the description includes a full <returns> block enumerating the success dict keys, cache/truncation/budget fields, and the three named failure modes. Combined with the visibility, rate-limit and idempotency notes, an agent has everything needed to call and interpret this tool.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so baseline is 3, but the description adds workflow meaning beyond the schema: how persist ties to agent_search_results materialization vs raw queryable rows, that filtering can be done via record_search_results verdicts, and how list_name buckets engagers. It does not add syntax detail, but it clarifies param interactions usefully.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource ('fetch the people who reacted to or commented on a LinkedIn post') plus the side effect ('store them as queryable engagement rows'), and explicitly scopes it to the user's own or anyone else's post. It is readily distinguishable from sibling query tools like query_linkedin_post_engagements from the first sentence.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Gives explicit when-to-use framing with user-intent examples ('everyone who liked this post'), then routes downstream: filter with query_linkedin_post_engagements using post_id, then queue outreach with a batched setup_linkedin_sequence passing provider_id. It also states the persist=False alternative and when to prefer it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Try in Browser

Glama MCP Gateway

Add one secure layer between your agents and this server.

Resources