Skip to main content
Glama

Analytics Legends — SAP Analytics Intelligence

Server Details

AI agent for SAP analytics: firms, day rates, contract radar, news, concepts, studies

Status
Healthy
Last Tested
Transport
Streamable HTTP
URL
Repository
analyticslegends/analytics-legends-mcp
GitHub Stars
0
Server Listing
ai.analyticslegends/sap-analytics

Glama MCP Gateway

Connect through Glama MCP Gateway for full control over tool access and complete visibility into every call.

MCP client
Glama
MCP server

Full call logging

Every tool call is logged with complete inputs and outputs, so you can debug issues and audit what your agents are doing.

Tool access control

Enable or disable individual tools per connector, so you decide what your agents can and cannot do.

Managed credentials

Glama handles OAuth flows, token storage, and automatic rotation, so credentials never expire on your clients.

Usage analytics

See which tools your agents call, how often, and when, so you can understand usage patterns and catch anomalies.

100% free. Your data is private.
Tool DescriptionsA

Average 4.6/5 across 20 of 20 tools scored.

Server CoherenceA
Disambiguation4/5

Each tool targets a distinct resource or action (firms, clients, modules, concepts, studies, opportunities, rates, news, knowledge graph). Some pairs like find_academy_modules vs list_sap_modules and find_sap_clients vs search_firms could be confused, but the descriptions explicitly disambiguate them.

Naming Consistency5/5

All tool names follow a consistent verb_noun pattern in lowercase snake_case: find_, get_, list_, search_, count_, query_. Verbs are consistently used for their roles (find/search for querying, get for single items, list for enumerations), with no mixed casing or style.

Tool Count4/5

20 tools is on the higher end, but the server covers a broad domain with multiple distinct datasets (directory, clients, academy, concepts, studies, opportunities, rates, news, graph). Each tool earns its place, though the count is slightly above the ideal 3-15 range.

Completeness5/5

The domain is a read-only intelligence platform, and it provides search/list and get operations for every major entity: firms, clients, modules, concepts, studies, and opportunities. The knowledge graph adds relational querying, and rates/news are covered. No essential lifecycle operations are missing for the stated purpose.

Available Tools

20 tools
count_firms_byCount the firm directory by country, kind, module or SAP signalA
Read-onlyIdempotent
Inspect

Answer a COUNTING question about the published firm directory in one call: how many organisations per country, per kind, per declared SAP module, or per SAP signal band — with the same country/kind/module/query filters search_firms takes, so you can count a slice as easily as the whole. Use this instead of paging search_firms and tallying rows: the directory holds thousands of organisations, and reading them all to produce a table of counts costs hundreds of calls and megabytes of rows for numbers Postgres computes in one scan. Every bucket is a value the directory actually stores; value: null is a real bucket meaning the field is unknown for those rows, and it is served rather than hidden — a country table that silently drops the rows with no country adds up to less than the population and says nothing about it.

ParametersJSON Schema
NameRequiredDescriptionDefault
byYesWhich facet to count on. Required — there is no default worth guessing.
kindNoRestrict to one organisation kind before counting, same vocabulary as search_firms. Combining it with `by:"kind"` is legal and returns that single bucket.
queryNoFree-text filter, matched case-insensitively.
moduleNoRestrict to organisations with a DECLARED link to one SAP module code before counting, same vocabulary as search_firms' `module`. Combining it with `by:"module"` is legal and returns that single bucket (plus the null bucket).
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

The description discloses that 'value: null' is a real bucket and is served rather than hidden, which is not obvious and could lead to misunderstanding. It also explains that every bucket corresponds to a stored directory value, not a computed bin. Since annotations already declare readOnlyHint and idempotentHint, the description adds valuable behavioral context about output semantics.

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

Conciseness5/5

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

The description is composed of three dense sentences: the first defines the purpose, the second explains why to use it over the alternative, and the third clarifies null bucket behavior. Every sentence earns its place without redundancy or filler.

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?

For a read-only aggregation tool with an output schema and robust annotations, the description covers the main decision points: what it does, when to use it, and a non-obvious behavioral characteristic. The output format is not described, but that is appropriately left to the output schema, so no meaningful gaps remain.

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

Parameters3/5

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

The schema documents all five parameters with descriptions and enums, achieving 100% coverage. The description only reiterates that filters are shared with search_firms and mentions that combining `kind` with `by:"kind"` is legal, but this is also present in the schema. No new parameter-level meaning is added.

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?

The description states the tool counts organizations in the firm directory by country, kind, SAP module, or SAP signal band. It explicitly uses the verb 'Answer a COUNTING question' and names the resource 'published firm directory', distinguishing it from search_firms, which is a sibling tool for listing rows.

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?

Directly instructs users to 'Use this instead of paging search_firms and tallying rows' and quantifies the cost of the alternative in calls and data volume. It also notes that the same filters as search_firms apply, so users can apply known filtering logic. This clearly states when to use the tool versus the most relevant sibling.

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

find_academy_modulesSearch the Academy training catalogueA
Read-onlyIdempotent
Inspect

Search the Analytics Legends Academy — the 303 written training modules on SAP Datasphere, Business Data Cloud, SAP Analytics Cloud, BW/4HANA and Databricks — by track, level and free text. Returns the catalogue entry: id, slug, EN/FR title, track, level, duration in minutes, tags and the editor's summary. DO NOT CONFUSE IT WITH list_sap_modules, which serves a different population under the same word: that one is the 40-row PRODUCT taxonomy (codes such as SAC, DATASPHERE) used to normalise product wording. This one is the course catalogue. CATALOGUE ONLY — the module BODY is subscriber content, served by get_academy_module on this same endpoint with a subscriber key (Consultant tier or above), which is the same door the €29.90 Consultant Pass opens on the site. status and is_preview are SERVED, never filtered on: they are the two flags the platform marks free access with, they do not coincide (measured 2026-08-16: 38 rows status='available', 56 rows is_preview), and you decide which one your answer needs. PAGINATED: pass _meta.next_cursor back as cursor with the same filters until it is null. Read _meta.available_tracks and _meta.available_levels — both counted on the served population at call time — before assuming a facet value exists.

ParametersJSON Schema
NameRequiredDescriptionDefault
levelNoRestrict to one level, matched case-insensitively: Beginner · Intermediate · Advanced · Expert. Counts in `_meta.available_levels`.
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
trackNoRestrict to one track, by SLUG (`databricks-data-eng`) or by English name (`Databricks & Data Eng.`), matched case-insensitively. The live vocabulary with per-track counts is `_meta.available_tracks` on every response. The numeric track_id is deliberately NOT accepted — it is an internal counter, and passing `6` would look like naming a subject.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Annotations already declare readOnlyHint=true and idempotentHint=true, so the safety profile is known. The description adds valuable behavioral context: pagination mechanics, the non-filterable `status`/`is_preview` flags measured on 2026-08-16, and the fact that the cursor is refused if filters change. This goes beyond annotations with actionable runtime details.

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?

The description is dense and every sentence provides value—disambiguation, scope, pagination, flags—with no filler. It is longer than a typical tool description, but given the tool's 5 params, sibling confusion, and non-obvious flags, the length is justified. The all-caps warnings help structure important caveats.

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?

Given the tool's complexity (5 params, output schema exists, two confusing sibling tools), the description is exceptionally complete: it covers purpose, return fields, differentiation from list_sap_modules, subscriber-only body via get_academy_module, pagination, measured flag counts, and meta usage. The only minor omission is explicit auth requirements for this search call, but the readOnlyHint and lack of a subscriber mention imply public access; the description is still thorough enough for reliable selection and invocation.

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% with detailed parameter descriptions, so the baseline is 3. The description adds marginal value by reinforcing the need to consult `_meta.available_tracks`/`available_levels` and explicitly stating `status`/`is_preview` are served but not filterable, which affects how parameters are used. It doesn't add new syntax or format, but it clarifies behavioral expectations around the schema.

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?

The description opens with 'Search the Analytics Legends Academy — the 303 written training modules...' which is a specific verb+resource with clearly enumerated subjects (SAP Datasphere, Business Data Cloud, etc.). It explicitly contrasts with list_sap_modules ('DO NOT CONFUSE IT WITH...') and defines the catalogue scope, leaving no ambiguity about what the tool does.

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?

The description provides explicit when-to-use guidance: it says 'CATALOGUE ONLY' and directs to get_academy_module for body content, and names list_sap_modules as a different population with a different purpose. It also gives operational instructions for pagination ('pass `_meta.next_cursor` back as `cursor`...') and advises reading `_meta.available_tracks`/`available_levels` before assuming facet values.

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

find_opportunitiesSearch the public SAP analytics contract radarA
Read-onlyIdempotent
Inspect

Search every SAP contract and permanent-role posting Analytics Legends publishes to an ANONYMOUS visitor — the same population a human browses on /opportunities/, where each posting has its own prerendered page. It merges the platform's TWO public legs, which are near-disjoint (measured 2026-07-30: 1 row in common): (a) the PROMOTED feed (public.public_opportunities) — general SAP work (FI/CO, SD, EWM, MDG, BTP, ABAP), all German cities, dated (posted_at is populated on EVERY active row of that leg — an invariant held since 2026-07-31, not a snapshot), and it carries NO rate, contract_type, currency or country_code: those fields come back null on that leg, so no rate or contract term can be read off it; (b) the SITE RADAR (/api/contracts-lean.json) — these carry country, category, seniority, posted_at, employment_type and, on most of them, expires_at; they are the analytics-specific ones (SAC Planning, Datasphere Technical Lead, Business Data Cloud). READ employment_type BEFORE CALLING THIS A CONTRACT MARKET: the radar is mostly PERMANENT roles, so an unfiltered page answers a freelance question with salaried jobs unless you filter. The argument of the same name does the filtering, and _meta.tranche_total_row_count on your own response is the live population — read the split from a filtered call, never from a figure quoted in this text. TWO DIFFERENT RATE FIELDS, AND THEY MEAN DIFFERENT THINGS. currency / daily_rate_min / daily_rate_max are the posting's OWN advertised rate and are almost always null — most listings publish no rate at all. rate_band is the platform's editorial benchmark for that posting's (seniority × product × region) cell, present on most rows, and it is what the posting's public page leads with. It is rate_basis: "panel_inferred" — Eursap n=312 plus the Analytics Legends operator panel, permanent rows restated as a TJM equivalent at ~220 billable days a year — NOT a rate this employer offered. Quote it as a band with its basis, kind and source, never as the posting's rate, and never average bands across postings: many rows share one cell. WHAT IS GATED IS A FIELD, NOT A ROW: on most radar rows source_url is null and application_link reads "members_only" — the verified link to the original listing is the paid Consultant-tier deliverable. Everything else about the posting is public, and citation_url is that posting's own page on analyticslegends.ai. Quote it. Report _meta.tranche_row_count as the published public population, never as the size of the market.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
countryNoISO-3166-1 alpha-2 code, applied to both legs as a predicate on the row's own country_code. It effectively selects the SITE-RADAR leg: the promoted feed leaves country_code NULL on all but a handful of its active rows, so a country filter drops the rest of that leg because they do not match, not because the leg was excluded by assumption. `_meta.match_count_by_leg` shows what each leg contributed on YOUR call — read the split there, never from a figure quoted in this text.
locationNoCity or place, matched case-insensitively as a substring of the posting's location. The promoted leg is all-German (Hamburg, Frankfurt am Main, Bremen, Munich, Cologne, Dortmund, Hanover, Landshut, Mannheim, Stuttgart); the site-radar leg is worldwide.
remote_modeNoRestrict to one work-location policy: `remote`, `hybrid` or `onsite`. READ THIS BEFORE ANSWERING A REMOTE QUESTION: a large share of the radar declares no policy at all (`_meta.remote_mode_undeclared` carries the live count — roughly half the radar when last measured, and a frozen pair written here drifted ~30% in two days), and an undeclared row is NOT an on-site row — it is a posting that does not say. Any value here therefore sets those rows aside rather than classifying them, exactly as the site's own filter does, and `_meta.remote_mode_undeclared` reports how many were set aside. The promoted leg carries its own `remote_mode` column and is filtered by the same predicate. Read `_meta.available_remote_modes` for the live spread before assuming a value exists.
employment_typeNoRestrict to one engagement type. THE RADAR IS MOSTLY PERMANENT, so a freelance or contract question answered off an unfiltered page is answered with salaried jobs. For the actual split, make the filtered call and read `_meta.tranche_total_row_count` — it is counted at query time. The promoted leg stores contract_type NULL on every one of its active rows, so any value here drops that leg by predicate — `_meta.note` says so.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

The description discloses far more than the annotations already signal: the near-disjoint nature of the two feed legs, date-sensitive invariants, gated fields (source_url null, application_link 'members_only'), the meaning of rate_band as an editorial benchmark, and the exact behavior of country/remote_mode/employment_type filters on each leg. This is exemplary behavioral transparency.

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

Conciseness3/5

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

Every sentence contains valuable information, but the description is a dense wall of text with all-caps emphasis and no paragraph breaks, making it hard to scan. It is not concise by any measure, though none of the content is fluff. The structure could be improved with bullets or sections.

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?

The tool is complex (two data legs, nuanced rate semantics, gated fields, pagination caveats) and the description covers all these facets with concrete guidance on reading _meta fields. Since an output schema exists, it need not enumerate return values, but it even references the relevant _meta fields the agent will encounter. This is complete for an agent to use the tool correctly.

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

Parameters5/5

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

Although schema coverage is 100%, the description adds crucial semantics beyond the schema: for employment_type it explains the radar is mostly permanent and that the promoted leg is dropped by predicate; for remote_mode it clarifies that undeclared rows are set aside, not classified; for country it explains how the promoted leg's null country_code causes rows to be dropped. These are meaningful additions that help an agent use parameters correctly.

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?

The description explicitly states the tool searches 'every SAP contract and permanent-role posting Analytics Legends publishes' and identifies the two public legs it merges. This is a specific verb+resource+scope, and it clearly differentiates this tool from sibling search tools by focusing on job/contract postings rather than firms, concepts, or news.

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

Usage Guidelines4/5

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

The description provides extensive context for correct usage: warnings to read employment_type before calling it a contract market, instructions to read _meta.tranche_total_row_count for the live split, and guidance on how to interpret rate_band vs daily_rate fields. However, it does not explicitly name alternative tools or state when to prefer them, so it stops short of a full 5.

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

find_sap_clientsSearch the SAP end-customer corpus (Legend tier)A
Read-onlyIdempotent
Inspect

Search the SAP END-CUSTOMER corpus — the companies that RUN SAP, not the firms that sell services (those are search_firms). This is the paid Legend+ dataset locked away from the public surface on 2026-07-08; it requires a subscriber API key, Legend tier or above. Verification status is SERVED, never silently filtered: sap_client_verification_status and status are columns on every row ('verified' on ~550 of ~21k rows), and you decide what standard of proof your answer needs. product filters on the detected-adoption flags every profile already carries (the uses_* columns get_sap_client_profile serves): it keeps only rows where that product was DETECTED. A row it drops is 'not detected by our detection pass', never 'does not use it' — detection is a positive signal with no negative counterpart.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.
productNoKeep only end-customers where this SAP product was DETECTED in use. Absence from the result means undetected, not unused.
industryNoIndustry or sector filter, matched case-insensitively.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Even with annotations declaring read-only and non-destructive, the description adds rich behavioral context: the dataset is 'locked away from the public surface,' verification status is 'SERVED, never silently filtered,' and product filtering is detection-based with no negative counterpart. These details go far beyond the annotations and clarify important data interpretation nuances.

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

Conciseness5/5

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

The description is a single dense paragraph, but every sentence delivers unique value: definition, access, verification behavior, and product semantics. There is no padding or repetition of schema details. The structure is front-loaded with the most critical context and flows logically.

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?

Given the tool's complexity (6 parameters, output schema, annotations), the description covers all key caveats: dataset nature, access restrictions, verification semantics, and filter interpretation. The output schema handles return values, and the schema descriptions cover the remaining parameters, so no critical information is missing.

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%, establishing a baseline of 3. The description adds extra semantic value by explaining the `product` parameter's detection-based behavior and linking it to the `uses_*` columns, which is not fully captured in the schema. It does not extensively cover other parameters, but the schema already handles them.

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?

The description opens with a clear, specific verb and resource: 'Search the SAP END-CUSTOMER corpus.' It immediately distinguishes from sibling search_firms by specifying 'the companies that RUN SAP, not the firms that sell services.' This makes the tool's purpose unambiguous and sets it apart from alternatives.

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?

The description provides explicit usage context: it is for finding SAP end-customers in a paid dataset, requires 'subscriber API key, Legend tier or above,' and points to search_firms as the alternative for service-provider searches. It also explains when verification status is directly served, guiding the agent on when to use this tool versus others.

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

get_academy_moduleRead an Academy module (Consultant tier)A
Read-onlyIdempotent
Inspect

Read one Academy training module in full — body, learning objectives and summary, EN and FR — the written course corpus the €29.90 Consultant Pass sells. Requires a subscriber API key (Authorization: Bearer alk_…), Consultant tier or above; without one this tool refuses and find_academy_modules keeps serving the catalogue. Takes the module id (M001) or its slug (datasphere-foundations), both matched case-insensitively — find_academy_modules returns both on every row, and query_knowledge_graph returns the same ids as module:M001 node ids, so a graph walk now ENDS somewhere. Unlike get_study, the whole module is served in one call: the longest body measured is 17 865 characters, two orders of magnitude under the response ceiling, so sectioning it would cost the caller context without protecting anything.

ParametersJSON Schema
NameRequiredDescriptionDefault
idYesModule id (`M001`) or slug (`datasphere-foundations`), verbatim from find_academy_modules.rows[].id / .slug.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Goes well beyond the readOnly/idempotent annotations by disclosing auth requirements, refusal behavior, case-insensitive id/slug matching, and even response size characteristics ('longest body measured is 17 865 characters'). This gives the agent deeper expectations about what will happen when the tool is invoked.

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?

Three long sentences, but each is information-dense and front-loaded: purpose in the first sentence, auth/alternatives in the second, input formats and call-size rationale in the third. No filler, though it could be tightened slightly without losing value.

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?

Covers what is returned (full module content, languages), who can use it (tier, API key), how the input maps to other tools, and why it is safe to return everything in one call. With a single parameter and rich annotations, this leaves no meaningful questions unanswered.

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?

The schema already fully describes the single `id` parameter with examples and provenance from find_academy_modules. The description adds the case-insensitivity detail and reinforces that both id and slug are accepted, which is semantically useful but not a major shift given the schema's high coverage.

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?

The description opens with a specific verb and resource: 'Read one Academy training module in full', listing contents (body, learning objectives, summary, EN/FR). It further distinguishes from siblings by referencing find_academy_modules and query_knowledge_graph, and contrasting with get_study, making the tool's unique role unmistakable.

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?

Explicitly states prerequisites ('Requires a subscriber API key... Consultant tier or above') and the consequence of lacking them ('without one this tool refuses and find_academy_modules keeps serving the catalogue'). It also advises when to use this over get_study ('Unlike get_study, the whole module is served in one call') and links to the catalogue and graph tools.

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

get_conceptGet one concept entry in fullA
Read-onlyIdempotent
Inspect

Fetch one concept entry by slug: title, category, level, tags and the editor's summary. Written by a named human editor, not generated. The card body, why-it-matters, key points and pro tip are subscriber content and are NOT returned — follow citation_url for those.

ParametersJSON Schema
NameRequiredDescriptionDefault
slugYesConcept slug from search_concepts.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

The annotations already declare read-only, idempotent, non-destructive behavior. The description adds valuable context beyond annotations: the content is human-written (not generated), and specific fields are subscriber-only and intentionally omitted. This explains behavior that annotations cannot convey and sets correct expectations.

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

Conciseness5/5

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

Two sentences, no wasted words. The first sentence leads with the action and key fields; the second clarifies exclusions and provides a next step (citation_url). Every clause adds value.

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?

For a single-parameter read tool with an output schema present, the description is complete: it specifies what is returned, what is omitted, and where to get more content. No gaps remain for the agent to misuse the tool.

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

Parameters3/5

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

Schema coverage is 100% and the single parameter 'slug' is already described as 'Concept slug from search_concepts.' The tool description repeats this and adds no new semantic detail about the parameter itself. Baseline 3 is appropriate since schema fully covers the parameter.

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?

The description clearly states the tool fetches one concept entry by slug, listing specific fields returned (title, category, level, tags, editor's summary) and explicitly distinguishes from sibling tools by noting what is not returned. The verb 'Fetch' and resource 'concept entry' are specific and unambiguous.

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

Usage Guidelines4/5

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

The description implies usage context: use for retrieving a concept summary, and if you need subscriber content, follow the citation_url. It does not explicitly name an alternative tool like get_concept_card, but the clear scoping of what is included and excluded serves as guidance. The reference to 'slug from search_concepts' also directs the user on how to obtain the parameter.

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

get_concept_cardFull concept card (Consultant tier)A
Read-onlyIdempotent
Inspect

The FULL encyclopaedia card for one concept — body, why-it-matters, key points, cheat sheet, glossary, pro tip, and the four analysis tables (decision table, peer comparison, named pitfalls, performance facts), EN and FR — the corpus the €29.90 Consultant Pass sells. Requires a subscriber API key (Authorization: Bearer alk_…), Consultant tier or above; without one this tool refuses and get_concept keeps serving the public metadata. Find slugs with search_concepts.

ParametersJSON Schema
NameRequiredDescriptionDefault
slugYesConcept slug, verbatim from search_concepts.rows[].slug.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint, covering the safety profile. The description adds valuable context about the authorization requirement, the refusal behavior without a valid key, and the fallback to the public metadata tool. This goes beyond the annotations without contradicting them, though it doesn't detail rate limits or error formats.

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

Conciseness5/5

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

The description is three sentences: the first front-loads the purpose and content, the second conveys the critical auth requirement and fallback, the third gives slug discovery guidance. Every sentence contributes value with no redundant wording.

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?

With a single parameter fully described in the schema, an output schema present, and annotations covering safety, the description supplies all remaining operational context: authentication, fallback to get_concept, card content, and slug discovery. It is complete for a read-only retrieval tool.

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

Parameters3/5

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

The input schema has 100% coverage, describing the slug parameter as 'verbatim from search_concepts.rows[].slug' and noting it's required. The description adds a pointer to search_concepts for slug discovery, which is useful but does not substantially alter parameter understanding. Baseline 3 is appropriate given the schema already carries the full burden.

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?

The description clearly states the tool retrieves the full concept card with specific content (body, why-it-matters, key points, etc.) in EN and FR. It explicitly distinguishes this from the sibling get_concept tool, which serves public metadata. The verb+resource+scope is precise.

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?

The description provides explicit when-to-use guidance (requires a subscriber API key and Consultant tier or above) and when-not-to-use (without it, the tool refuses and get_concept serves public metadata). It also directs users to search_concepts for finding slugs. This clearly differentiates the tool from alternatives and covers prerequisites.

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

get_day_rate_benchmarkPublic SAP analytics day-rate aggregateA
Read-onlyIdempotent
Inspect

The PUBLIC day-rate aggregate for SAP analytics freelance work: min/max daily rate by country, specialisation and seniority, each row carrying its own currency, source, source date and confidence. This is the free aggregate published at analyticslegends.ai/api/market-rates.json, and it is SMALL — 11 rows on 2026-08-09, every one of them a secondary source (a published market study or a job-board scan), sample_size null on 8 of them. NOTHING IS HELD BACK BEHIND IT: there is no paid counterpart to this aggregate. The community-contribution path exists (public.rate_contributions) but publishes nothing yet — v_community_rate_aggregates and v_rate_index are still empty, because a contributed rate only surfaces once a cell holds enough submissions to be reported without identifying anyone. So whatever percentile a source row happens to carry is served here, free, to everyone. The GB row carries a median, p10 and p90, and its own note says its min/max ARE the 25th and 75th percentiles. What is missing from this answer is missing from THIS aggregate; it is not a paid tier. THIS IS NOT THE ONLY RATE THE PLATFORM PUBLISHES, AND ON THE QUESTIONS THIS MARKET ASKS MOST IT IS THE THINNER ONE. find_opportunities returns a rate_band on most live radar postings — a panel-inferred P25–P75 band per (seniority × product × region) cell, Eursap n=312 plus the Analytics Legends operator panel, and it is what each posting's public page leads with. It prices exactly the cells this small aggregate cannot — Senior Datasphere DACH, Senior BDC DACH — where specialisation:"bdc" here returns nothing. When this tool comes back empty for a country × product, say the AGGREGATE holds no row and go read the radar band — do not report that the platform cannot price it. The two are different instruments: this one is a published market study, that one is an editorial benchmark attached to a live posting. Read _meta.available_countries / available_specialisations / available_seniorities — they are computed from the aggregate on every call — before concluding that a rate is unpublished, and quote each row with its own currency, its confidence and its source date.

ParametersJSON Schema
NameRequiredDescriptionDefault
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.
seniorityNoe.g. senior, principal.
specialisationNoOne of the codes the aggregate actually holds — analytics_all, bw, bw4hana, bw4hana_sac, sac, datasphere (2026-08-09; the live list comes back as `_meta.available_specialisations` on every call). They are NOT evenly spread across countries: DE holds analytics_all only, at three seniorities, and datasphere exists for FR alone, as a median with confidence 'low'. There is no bdc row and no joule row in THIS aggregate — but the platform does price BDC: `find_opportunities` carries a panel-inferred band on the live postings, €1,000–€1,400/day P25–P75 for Senior BDC on 52 German postings (2026-08-10). A code this aggregate does not hold returns 0 rows and the available codes; it never widens to a neighbouring band, and 0 here does not mean the platform is silent.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the readOnlyHint annotation, the description discloses crucial behavioral traits: the aggregate is small (11 rows), rows are secondary sources, sample_size is null on 8 rows, there is no paid counterpart, community views are empty, and unsupported codes return 0 rows plus available codes. It also explains the GB special case and the availability of _meta fields.

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

Conciseness3/5

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

The description is front-loaded with the core definition and contains essential caveats, but it is overly verbose and repetitive, using ALL CAPS and lengthy emphatic sections. While each sentence adds information, the overall length may hinder readability; a more condensed structure would be preferable.

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?

The description is fully complete given the tool's complexity: it covers purpose, data provenance, limitation examples, relationship to find_opportunities, parameter semantics, runtime metadata, and behavior on empty results. It leaves no ambiguity for an agent, making it self-contained.

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

Parameters5/5

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

Even though the schema already describes all three parameters with 100% coverage, the description adds significant semantics, especially for the specialisation parameter. It lists live codes (analytics_all, bw, bw4hana, sac, datasphere), notes uneven distribution (DE holds analytics_all only), and clarifies behavior for unsupported codes (returns 0 rows and available codes). This far exceeds schema-level documentation.

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?

The description clearly identifies the tool as 'The PUBLIC day-rate aggregate for SAP analytics freelance work' and specifies the data returned (min/max daily rate by country, specialisation and seniority). It also distinguishes this tool from the sibling tool find_opportunities, making its purpose unambiguous.

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?

The description explicitly instructs when to use this tool vs find_opportunities, noting the aggregate is 'the thinner one' and directing users to consult the radar band when the aggregate holds no row. It names the alternative tool and even provides concrete examples (Senior Datasphere DACH, Senior BDC DACH) where the alternative is preferred.

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

get_firmGet one firm's published profileA
Read-onlyIdempotent
Inspect

Fetch one organisation from the published directory by its database slug (rows[].slug from search_firms, verbatim). Returns the same public fields plus partnerships_declared, the count of partnerships this directory records for the firm — 0 on ~97 % of rows (re-measured 2026-08-14 on the published tranche: 96,8 %), meaning none declared here, never that the firm has no partners. Does not return the paid firm-intelligence profile, contacts, or any person.

ParametersJSON Schema
NameRequiredDescriptionDefault
slugYesThe DATABASE slug, taken verbatim from search_firms.rows[].slug. It is not always the web slug in citation_url: a minority of published rows carry a numeric firm id instead (365 of them on 2026-08-09 — the population is read at query time and returned as `_meta.tranche_total_row_count`, never written down here). get_firm{slug:"00393"} is GULP, whose page is /companies/gulp/. Deriving a slug from the citation URL fails on those rows, and deriving it from the NAME is not safe either; carry rows[].slug across instead. A slug this tool refuses is not proof the firm is absent from the market or even from the database — the published tranche is an editorial subset, and a row the editor has not published is refused here exactly as a wrong slug is.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the annotations (readOnly, idempotent, destructiveHint false), the description adds critical behavioral context: it explains that `partnerships_declared` being 0 means none declared, not that the firm has no partners, and provides measured frequency data. It also notes that a refused slug does not mean the firm is absent, because the published tranche is an editorial subset. This is valuable nuance not captured in annotations.

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?

The description is efficiently structured: an action sentence, a return-semantics sentence, and an exclusions sentence. It is slightly dense due to the parenthetical measurement detail ('re-measured 2026-08-14... 96,8 %'), but every clause contributes to understanding. It is front-loaded and appropriately sized for a tool with this nuance.

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?

Given the presence of an output schema and annotations, the description is complete. It explains the key return field's semantics and the potential misinterpretation, while the schema covers slug handling in depth. No important behavioral or usage aspects are left undocumented for the tool's complexity.

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

Parameters3/5

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

With schema description coverage at 100%, the baseline is 3. The tool description merely recaps the slug source ('rows[].slug from search_firms') already fully detailed in the schema, adding no new parameter semantics. The schema itself contains extensive guidance on numeric slugs and refusal behavior, but that belongs to the schema, not the tool description.

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?

The description clearly states the action ('Fetch one organisation from the published directory') and the specific resource ('published profile'), using the verb 'Fetch' with a precise scope. It distinguishes from siblings by noting it returns public fields and does not return the paid firm-intelligence profile or contacts, making its purpose unambiguous.

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

Usage Guidelines4/5

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

The description implies when to use the tool (when a single firm's published profile is needed) and tells the user to source the slug from search_firms, noting that the slug is taken verbatim. It also states exclusions (no paid profile, contacts, or persons), which hints at alternatives, but it does not explicitly name tools like get_firm_intel or search_firms for those needs.

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

get_firm_intelFirm intelligence profile (Legend tier)A
Read-onlyIdempotent
Inspect

The paid intelligence profile of a services firm — SAP practice size and partner level, delivery flags per product, typical day rate and seniority, notable clients, analytics practice summary, and a LinkedIn company URL (present on ~39% of the corpus — glassdoor_rating, glassdoor_reviews_count and linkedin_followers are null on the entire corpus as of 2026-08-10, absence here is a data gap, not a signal). Requires a subscriber API key, Legend tier or above. Person-shaped fields (contacts, founders, leadership, recruiters, postal addresses) are NEVER served by this endpoint at any tier — they remain behind the platform's signed-URL path. Search by name; the public directory (search_firms) is a different, wider population.

ParametersJSON Schema
NameRequiredDescriptionDefault
modeNoKeep only firms whose profile declares this engagement mode (mode_freelance / mode_permanent / mode_subcontract). Same reading as `delivers`: declared-only.
nameNoFirm name, matched case-insensitively. Omit to browse the corpus by data completeness.
limitNoMax rows (hard cap 10 — these rows are wide).
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.
deliversNoKeep only firms whose profile DECLARES delivery of this product (the `delivers_*` flags every row already carries). An undeclared flag drops the row: absence from the result means the profile does not declare it, not that the firm cannot deliver it.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the annotations (readOnly, idempotent, non-destructive), the description adds critical behavioral context: requires a subscriber API key and Legend tier, explains that LinkedIn follower counts are null on the entire corpus and absence is a data gap not a signal, and reveals that person-shaped fields are never served even though they might be expected. This goes well beyond what annotations provide.

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

Conciseness5/5

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

The description is a single dense paragraph but every sentence earns its place: purpose, data caveat, authentication requirement, explicit exclusion of fields, and search guidance. It is front-loaded with the core purpose and efficiently packs caveats without redundancy. No filler or repeated schema content.

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?

Given the tool's complexity (6 params, output schema, annotations), the description is complete: it explains what the profile includes and excludes, notes data completeness caveats, specifies tier/auth requirements, and points to the correct alternative for excluded data. It fully equips an agent to decide when and how to invoke this endpoint.

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

Parameters3/5

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

The schema description coverage is 100% with detailed parameter descriptions (e.g., mode enums, cursor semantics, delivers flags). The tool description itself does not re-explain any individual parameter, so it adds no additional parameter-level meaning. The baseline of 3 applies because the schema already carries the full burden.

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?

The description uses a specific verb ('get') with a concrete resource ('firm intelligence profile'), enumerating exactly what the profile contains (SAP practice size, partner level, delivery flags, day rate, notable clients, analytics summary, LinkedIn URL). It further distinguishes itself from the sibling search_firms by noting the public directory is 'a different, wider population,' and explicitly states that person-shaped fields are never served by this endpoint, setting clear boundaries.

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?

Explicitly states when to use: for a paid, Legend-tier intelligence profile, searched by name. It gives a clear when-not-to-use: person-shaped fields (contacts, founders, leadership, etc.) are NEVER served here, and directs users to the platform's signed-URL path. It also contrasts with search_firms, providing an alternative. This is explicit guidance with exclusions and alternatives.

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

get_sap_client_profileOne SAP end-customer profile (Legend tier)A
Read-onlyIdempotent
Inspect

The full profile of one SAP end-customer — SAP footprint (products in use, modules known), analytics solutions, identity and evidence fields. Requires a subscriber API key, Legend tier or above. id comes verbatim from find_sap_clients.rows[].id.

ParametersJSON Schema
NameRequiredDescriptionDefault
idYesProfile id, verbatim from find_sap_clients.rows[].id.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnly, idempotent, and non-destructive, so the description adds value by disclosing the API key/tier requirement and the source of the id. It does not contradict annotations and provides meaningful operational context beyond the schema.

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

Conciseness5/5

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

Two compact sentences. The first states the purpose and content; the second covers auth and id provenance. No filler or repetition of annotations.

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?

For a simple single-parameter retrieval tool with an output schema present, the description covers purpose, content, auth, and id provenance. It is sufficiently complete to guide correct invocation without needing to explain return values.

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 already covers the only parameter with 100% coverage. The description adds extra semantic value by explicitly stating that `id` comes verbatim from find_sap_clients.rows[].id, reinforcing correctness of parameter use beyond the schema's brief label.

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?

The description specifies a singular, concrete resource: the full profile of one SAP end-customer with listed content domains (SAP footprint, analytics, identity, evidence). It clearly distinguishes from the sibling find_sap_clients by referencing a specific id from that list.

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

Usage Guidelines4/5

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

States the prerequisite (subscriber API key, Legend tier) and tells the agent that the id should come from find_sap_clients.rows[].id, implying the natural workflow: first list, then get detail. It does not explicitly mention when not to use alternatives, but the referential guidance provides sufficient usage direction.

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

get_studyRead a study (Consultant tier)A
Read-onlyIdempotent
Inspect

Read one Analytics Legends study BODY — the paid text behind list_studies' metadata. Requires a subscriber API key, Consultant tier or above. Bodies run to 38k words and exceed the 256 KiB response ceiling, so this tool serves STRUCTURE first: called without section it returns the section list and the introduction; pass section (a heading from that list, matched case-insensitively) to read one section. Find slugs and languages with list_studies.

ParametersJSON Schema
NameRequiredDescriptionDefault
langNoISO-639-1 language of the edition, e.g. en or fr. Defaults to en.en
slugYesStudy slug, verbatim from list_studies.rows[].slug.
sectionNoA section heading from a previous call's `sections` list. Omit to get the list.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the annotations (readOnly, idempotent, non-destructive), the description discloses significant behavioral traits: a subscriber API key and Consultant tier requirement, the 256 KiB response ceiling, the structure-first behavior, case-insensitive section matching, and inclusion of the introduction. This is rich context useful for an agent.

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

Conciseness5/5

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

Every sentence earns its place: purpose, auth constraint, size limitation, usage mechanism, and pointer to list_studies. The description is front-loaded with the core action and then methodically explains the chunked reading approach without redundancy. Length is justified by the tool's complexity.

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?

Given the tool's complexity (auth tier, size limit, section-based reading) and the presence of an output schema, the description fully covers how to invoke it correctly: what to pass, what to expect, and where to get inputs. No critical usage aspect is missing.

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 coverage is 100%, so baseline is 3. The description adds value by noting that `section` matching is case-insensitive and that omitting `section` returns not just the section list but also the introduction. It also clarifies that `slug` is verbatim from list_studies, reinforcing schema hints.

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?

The description opens with a specific verb+resource: 'Read one Analytics Legends study BODY — the paid text behind list_studies' metadata.' This clearly distinguishes it from sibling list_studies and other get_* tools by focusing on the full text body, not metadata or other entity types.

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?

It explicitly tells when to use this tool vs list_studies: 'Find slugs and languages with list_studies.' It also provides a full usage pattern: call without `section` for the section list and introduction, then pass a section heading for one section. No exclusions are needed because the alternative is named.

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

list_firm_kindsList firm kinds with live countsA
Read-onlyIdempotent
Inspect

Breakdown of the published firm directory by organisation kind, with a live row count per kind. Use this before search_firms to know what the population actually is instead of guessing.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint=false, covering the safety profile. The description adds useful behavioral detail: the counts are 'live', indicating freshness and that the data reflects the current state, which is not conveyed by annotations or schema.

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

Conciseness5/5

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

The description is two sentences, front-loaded with the core function and then a practical usage hint. Every word earns its place, with no redundancy or filler.

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?

Given the simple parameterless signature, rich annotations, and presence of an output schema, the description provides sufficient context for an agent to understand the tool's role and when to invoke it. It adds domain context (published directory, live counts) and usage guidance, making it complete for this tool's complexity.

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?

There are no parameters, so the description carries no parameter burden. The baseline for zero parameters is 4, and though the description doesn't add parameter-specific meaning, it explains the output grouping by organization kind, which helps set expectations for the result.

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?

The description clearly states the tool provides a breakdown of the published firm directory by organization kind, with live counts. It distinguishes itself from sibling tools like search_firms by focusing on population-level aggregation rather than individual firm lookup, and explicitly frames it as a precursor to searching.

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

Usage Guidelines4/5

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

The description explicitly says to use this tool before search_firms, providing clear context and a naming the alternative. It lacks explicit 'when not to use' exclusions, but the guidance to use it as a preliminary step is direct and helpful.

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

list_freelance_platformsList the CV/profile platforms a consultant can sign up onA
Read-onlyIdempotent
Inspect

The subset of the published directory where a consultant can CREATE A PROFILE — freelance marketplaces, job boards with candidate profiles, talent platforms and expert networks — each with its signup URL, an editorial confidence grade and the date it was assessed. This answers the entering-contractor's first practical question ('where do I register?') in one call; until 2026-08-16 the flag existed on ~106 published rows and no tool could list them. Everything here is also in search_firms — this tool adds the platform fields and the filter, never a wider population. signup_url is the platform's own page: it was verified on assessed_at, and a platform absent here is not proven to refuse signups — it is unassessed or unpublished.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.
platform_typeNoRestrict to one platform type, lowercase snake_case. The live vocabulary with counts is `_meta.available_platform_types` on every response — a well-formed unknown value returns no rows, it never widens the result.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the annotations (readOnlyHint, idempotentHint, etc.), the description discloses valuable behavioral nuances: that signup_url was verified on assessed_at, that absence of a platform does not prove refusal (only that it's unassessed or unpublished), and that the tool is a subset of the directory. This context prevents misinterpretation of results and enriches the agent's understanding without contradicting annotations.

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?

The description is well-structured and front-loaded with the core purpose. The historical note about 2026-08-16 and the count of rows is marginally useful but adds length; the relationship to search_firms and the absence caveat are essential. Overall it is efficiently written, earning a 4 rather than 5 due to a slightly verbose historical aside.

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?

Given the presence of a rich output schema and detailed input schema, the description still adds complete context: it defines the result population, the fields returned (signup_url, confidence grade, assessed_at), the filter semantics, and the caveat about absent platforms. The tool is fully specified for an agent to select and invoke appropriately.

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

Parameters3/5

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

The input schema already provides 100% parameter coverage with descriptions for limit, cursor, country, and platform_type. The description adds no parameter-specific semantics beyond the schema; it contextualizes the tool's purpose but not individual parameters. Per calibration rules, baseline 3 applies due to full schema coverage.

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?

The description clearly defines the tool as listing a subset of the published directory where consultants can create profiles, enumerating the categories (freelance marketplaces, job boards, talent platforms, expert networks) and the returned fields. It explicitly distinguishes this tool from the sibling search_firms by stating it adds platform fields and the filter, never a wider population.

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?

The description states when to use this tool: to answer the entering-contractor's registration question in one call. It explicitly identifies search_firms as the alternative for the broader population, saying 'Everything here is also in search_firms' and clarifying that this tool adds platform fields and the filter. It also provides a caution about the interpretation of absent platforms, guiding correct usage.

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

list_sap_modulesSAP analytics module taxonomyA
Read-onlyIdempotent
Inspect

The canonical SAP module/product taxonomy Analytics Legends classifies against (codes and EN/FR labels by category). Use it to normalise a user's loose product wording — 'SAC', 'Analytics Cloud', 'Datasphere' — onto the codes the other tools filter on.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnlyHint=true, idempotentHint=true, destructiveHint=false, so the safety profile is well covered. The description adds value by explaining the taxonomy's content (codes, EN/FR labels, categories) and its role as a lookup/reference. No contradictions with annotations.

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

Conciseness5/5

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

Two sentences, zero waste. The first sentence states what it is, the second explains the exact use case with illustrative examples. The structure is front-loaded and purposeful.

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?

The tool has an output schema and rich annotations, so return values and safety are covered elsewhere. The description fills the remaining gaps: why this tool exists, how it relates to sibling tools, and what kinds of inputs it handles. This is complete for an agent to decide when to invoke it.

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

Parameters3/5

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

Schema coverage is 100%, with each parameter (limit, query, cursor) already defined in the schema. The description adds no parameter-specific semantics but doesn't need to; the baseline of 3 is appropriate given the high schema coverage.

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?

The description clearly identifies the resource (canonical SAP module taxonomy), the action (list/classify), and the role (normalise user wording onto codes). It distinguishes from siblings by noting the codes are what other tools filter on, with concrete examples like 'SAC', 'Analytics Cloud', 'Datasphere'.

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

Usage Guidelines4/5

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

It explicitly states when to use the tool: to normalise loose product wording into canonical codes for other tools. It gives a clear use case but does not name alternative tools or exclusion scenarios. The reference to 'other tools' is enough context for an agent.

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

list_studiesList the deep-research studies (metadata only)A
Read-onlyIdempotent
Inspect

List the Analytics Legends deep-research studies with their edition, as-of date, audience, word count and canonical URL. METADATA ONLY: study bodies are a paid Consultant-tier deliverable, served by get_study on this same endpoint with a subscriber key. Use this to tell a reader that a study exists and where to read it.

ParametersJSON Schema
NameRequiredDescriptionDefault
langNoLanguage code, EN or FR.
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnly, idempotent, and non-destructive behavior. The description adds that this is metadata-only, that bodies are a paid deliverable via `get_study`, and the exact fields returned. This goes beyond annotations to disclose important behavioral scope, though it doesn't mention pagination or error behavior.

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

Conciseness5/5

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

Three sentences, each adding value: purpose, metadata-only caveat with alternative, and use case. No redundancy or unnecessary elaboration; it is concise and well-structured.

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?

Given the output schema exists and annotations cover safety, the description provides complete context for a list tool: what it returns, the metadata-only constraint, and how to direct users to full studies. It is sufficiently complete without needing to explain return values in detail.

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

Parameters3/5

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

Schema description coverage is 100%, with each parameter (lang, limit, query, cursor) having a detailed description. The tool description does not repeat parameter details, which is acceptable given the high schema coverage; it adds no extra parameter semantics beyond the schema.

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?

The description states a specific verb ('List') and resource ('deep-research studies'), scopes to 'metadata only', lists the exact fields returned (edition, as-of date, audience, word count, canonical URL), and explicitly contrasts with sibling tool `get_study`. This clearly distinguishes it from related tools.

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?

It explicitly says to use this tool to tell a reader that a study exists and where to read it, and states that study bodies are served by `get_study` with a subscriber key. This provides clear when-to-use guidance and names the alternative tool.

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

query_knowledge_graphTraverse the learning knowledge graphA
Read-onlyIdempotent
Inspect

The RELATIONS between the platform's teaching objects — which Academy module teaches which concept, which study covers which module, what a concept relates to. THIS IS THE ONLY TOOL ON THIS SERVER THAT SERVES EDGES; the other sixteen serve rows. Ask it what connects to what, not what exists. SCOPE, AND IT IS NARROWER THAN 'the knowledge graph': it carries four node types — concept, module, study, vendor — and every edge whose BOTH endpoints are one of them. The whole graph holds eleven node types; the seven it does not carry are each either served by their own tool or named as not served at all, and _meta.excluded_node_types says which per type (consultant data is served at NO tier), so a missing type is a documented boundary and never a silent gap. Call it with node_id (e.g. module:M178, concept:C001, study:ai-impact-2026-EN) to walk one node's neighbourhood; with node_type and/or query to find a node id first. edge_type and direction narrow a walk. Read _meta.available_edge_types — computed from the served projection on every call — before assuming an edge type exists.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoCase-insensitive substring of a node's label. Applies to the NODE listing, not to a walk.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
node_idNoFully-qualified node id, `<type>:<id>` — `module:M178`, `concept:C001`, `study:ai-impact-2026-EN`, `vendor:alteryx`. With it, rows are that node's EDGES (one row per neighbour). Without it, rows are NODES.
directionNoWhich side of the edge `node_id` must sit on. Default `both`. Ignored without `node_id`, and the response says so rather than pretending it applied.
edge_typeNoRestrict a walk to one relation (teaches · taught_by · covers · related). Read `_meta.available_edge_types` — it is computed, never written here.
node_typeNoRestrict to one carried node type: concept · module · study · vendor. Read `_meta.available_node_types`.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Annotations already declare readOnly, idempotent, non-destructive. The description adds rich behavioral context beyond that: cursor is bound to filters and refused if changed, direction is ignored without node_id and the response explicitly says so, available_edge_types is computed per call, and missing node types are documented boundaries not silent gaps. No contradiction with annotations.

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

Conciseness5/5

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

The description is long but every sentence carries unique, actionable information. It starts with the primary purpose and the key distinction, then covers scope, node types, calling patterns, and edge cases. There is no fluff or repetition; each section earns its place.

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?

The tool has a comparatively complex scope (four node types, edge filtering, pagination, cursors) and an output schema. The description covers the scope boundaries, exclusions, meta fields, interaction between parameters, and cursor behavior. This is fully complete for an agent to invoke it correctly without prior knowledge.

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

Parameters5/5

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

Even though schema coverage is 100%, the description adds substantial semantic value: fully-qualified node_id format with concrete examples, explanation that node_id yields edges vs nodes, direction behavior when ignored, cursor semantics, and the need to consult computed _meta.available_edge_types. This goes far beyond the schema's field descriptions.

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?

The description is explicit and specific: it states the tool serves RELATIONS/edges in the knowledge graph, with a clear verb ('traverse', 'ask what connects to what') and resource. It distinguishes itself from all other tools on the server by being the only edge-serving tool, making its purpose unmistakable.

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?

It provides explicit when-to-use guidance: 'Ask it what connects to what, not what exists' and names the alternative (other sixteen tools serve rows). It also details how to invoke with node_id, node_type, query, and tells users to read _meta.available_edge_types before assuming an edge type exists. This is exemplary usage guidance.

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

search_conceptsSearch the SAP analytics concept encyclopaediaA
Read-onlyIdempotent
Inspect

Search the SAP analytics concept encyclopaedia — the vocabulary of the stack, written for practitioners. Returns titles and summaries; call get_concept for the full entry.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
categoryNoConcept category, matched case-insensitively as an exact value OR a prefix — so category:"datasphere" reaches 'Datasphere Core'. The values are long human labels, not codes. DO NOT GUESS THEM FROM THIS TEXT: the live vocabulary with a row count per label comes back as `_meta.available_categories` on EVERY call, including a call that matched nothing. A list written here would say 14 labels with 2026-07-30 counts; the corpus holds 15 today, and five of those counts have moved. Read the envelope, not the prose.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior4/5

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

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false. The description adds the behavioral trait that results return titles and summaries, not full entries, which helps set expectations. It does not contradict annotations.

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

Conciseness5/5

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

The description is just two sentences, front-loaded with the tool's purpose and followed by the return format and a pointer to the sibling tool. Every word earns its place, with no redundancy.

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?

Given the tool has an output schema, the description does not need to explain return values. It covers purpose, return type, and the complementary get_concept tool. The schema handles parameter details, and annotations cover safety, making the description complete for tool selection.

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

Parameters3/5

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

Schema description coverage is 100%, with detailed descriptions for all four parameters (limit, query, cursor, category). The description adds no parameter semantics beyond what the schema already provides, so baseline 3 is appropriate.

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?

The description clearly states the verb ('Search') and the resource ('SAP analytics concept encyclopaedia'), and distinguishes from sibling get_concept by noting it returns titles and summaries while get_concept provides the full entry.

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

Usage Guidelines4/5

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

It provides context for when to use this tool versus the alternative get_concept: 'call get_concept for the full entry.' It does not explicitly exclude other sibling searches, but the domain-specific resource name makes the intended use evident.

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

search_firmsSearch the SAP analytics firm directoryA
Read-onlyIdempotent
Inspect

Search the published Analytics Legends directory of SAP analytics service providers — placement agencies, Big-4 and ESN practices, SAP vendors, platforms and community groups — by country, kind, declared SAP module and free text. Returns name, HQ country/city, website, careers URL and a one-line editorial claim. SAP END-CUSTOMER companies are NOT in this directory: they are a separate paid dataset, excluded here by the is_client FLAG — not by the client_enterprise kind code. The two are different columns, and where a row's flag and its kind label disagree in the SSOT it is the flag that decides what this tool serves, so read the flag's meaning into the answer and not the label's. PAGINATED: the whole matched set is reachable — pass _meta.next_cursor back as cursor with the same filters until it is null. When query is set, rows are ordered by how well the NAME matches it (exact, then prefix, then substring), and rows matching only the description come last; without query the order is the directory's own quality ranking.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindNoRestrict to one organisation kind. This list is the vocabulary the corpus holds today, not a frontier — call list_firm_kinds for the live one. A malformed code is refused; a well-formed code the corpus does not hold returns no rows. Neither case is silently ignored, and neither widens the result.
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
moduleNoRestrict to organisations with a DECLARED link to one SAP module/product code (UPPERCASE snake_case, e.g. DATASPHERE, BDC, SAC, BW4HANA, S4HANA, JOULE — case-insensitive on input). The declared links are structured data, far more selective than free text: `count_firms_by {by:"module"}` gives the live vocabulary with counts. A minority of the directory declares any module at all, so this filter finds the DECLARED specialists — absence from the result means no declared link, never that the firm does not work on the module.
countryNoISO-3166-1 alpha-2 country code, e.g. DE, FR, CH.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Annotations already declare read-only, idempotent, and non-destructive traits, so the description adds substantial behavioral nuance beyond them: the is_client flag vs kind column disagreement and which one decides results, the full pagination mechanism with cursor semantics, query-based ordering, and the module filter's 'declared link' meaning. These are critical execution details an agent would otherwise not know.

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?

The description is a single dense paragraph but is front-loaded with the core purpose and return fields, then proceeds logically through exclusions, flag semantics, pagination, and ordering. Every sentence carries meaningful information, though the prose is long and could benefit from bullet points for faster scanning.

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?

Given the tool's complexity—multiple filters, pagination, a subtle flag-vs-kind distinction, and query-dependent ordering—the description covers all critical behavioral aspects. It explains what the tool returns, how pagination works, how filters interact, and how to interpret empty results. The output schema likely covers field-level types, so no significant gaps remain.

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

Parameters5/5

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

Schema coverage is 100%, but the description significantly enriches each parameter's meaning: it warns that 'kind=client_enterprise' is not the actual discriminator (the is_client flag is), explains the ordering for 'query', emphasizes that 'cursor' must reuse the same filters, and clarifies that 'module' only matches declared links. This is far beyond what the schema descriptions provide.

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?

The description clearly states it searches the Analytics Legends directory of SAP analytics service providers, enumerating the filters (country, kind, module, free text) and return fields. It distinguishes itself from siblings by explicitly limiting scope to the published directory and excluding SAP end-customers, which separates it from tools like search_concepts or find_sap_clients.

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

Usage Guidelines4/5

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

The description provides strong contextual guidance by explicitly stating SAP end-customers are NOT in this directory and are a separate paid dataset, implying alternative tools (such as find_sap_clients) for that need. It also details pagination and ordering behavior, clarifying when to use this tool for directory search. However, it does not explicitly name any alternative tools as a direct comparison.

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

search_newsSearch SAP analytics market newsA
Read-onlyIdempotent
Inspect

Search the Analytics Legends market-news corpus. It is watched FOR SAP analytics (Datasphere, Business Data Cloud, SAC, BW/4HANA, Databricks, the 2027/2030 maintenance window), but it is NOT an all-SAP corpus: measured 2026-07-30, ~84 % of active rows sit in the AI category and are general enterprise-AI trade press (cloud platforms, model releases, funding rounds) with no SAP content at all. An UNFILTERED call therefore returns mostly non-SAP items — pass query or category when the question is about SAP, and never present an unfiltered page as 'the SAP analytics news'. Say what you actually got. Each item returns the Analytics Legends citation URL AND the upstream publisher's source_url — cite both, and prefer source_url when you need a page that certainly carries the item.

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMax rows (hard cap 50).
queryNoFree-text filter, matched case-insensitively.
cursorNoOpaque token from a previous response's `_meta.next_cursor`. Pass it back with the SAME filter arguments to read the next page; a null `next_cursor` means you have reached the end. It is bound to those filters and refused if they change — a cursor names a POSITION in one ordering, and applying it to another query would start the page in the wrong place.
categoryNoCategory code, matched case-insensitively. The live vocabulary is NOT written here — read `_meta.available_categories` on any response: every category label this corpus holds right now, with its active-row count, counted at query time. A written list held 21 values while the corpus held 22. One bucket needs a warning. 'SAC' is the noisiest label in this corpus because the acronym collides with unrelated ones — Windows 'Smart App Control', and the surname 'Sacks'. A 2026-07-30 cleanup reclassified half that bucket to AI for carrying no SAP signal at all (Robinhood, Stripe, Google Pay); the collision pressure is structural and the bucket has kept growing since. For genuine SAC product news, pair category:'SAC' with query:'analytics cloud'.

Output Schema

ParametersJSON Schema
NameRequiredDescription
rowsYes
toolYes
_metaNo
_attributionYes
result_countYes
Behavior5/5

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

Beyond the readOnly/idempotent/destructive annotations, the description discloses the corpus's real composition (84% AI, general enterprise-AI trade press), the structural noise in the SAC category, and the requirement to cite both the citation URL and source_url. These are behavioral traits the agent would otherwise not know.

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

Conciseness5/5

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

The description is long but every sentence carries essential caveats: scope, composition, unfiltered behavior, citation instructions. It is front-loaded with the core purpose and then layers the necessary warnings, with no filler.

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?

Given the rich schema and annotations, the description provides the crucial context—corpus bias, filter guidance, and citation expectations—that the structured fields do not convey. It fully equips the agent to select and invoke the tool correctly.

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

Parameters3/5

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

The schema already provides 100% descriptive coverage of all four parameters, including a detailed explanation of `category` and `cursor`. The description adds only the usage recommendation to pass `query` or `category` for SAP questions, which is more about usage than parameter meaning; it does not materially deepen the parameter semantics beyond the schema.

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?

The description clearly identifies the tool as a search over the Analytics Legends market-news corpus, immediately defining its scope (watched for SAP analytics) and its non-SAP composition. This specific verb+resource+scope statement distinguishes it from sibling search tools.

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?

It explicitly tells the agent when to pass `query` or `category` for SAP-related questions, warns that unfiltered calls return mostly non-SAP items, and instructs never to present an unfiltered page as 'the SAP analytics news'. It also directs the agent to say what it actually got, providing clear usage context.

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

Discussions

No comments yet. Be the first to start the discussion!

Related MCP Servers

  • A
    license
    A
    quality
    B
    maintenance
    AI access to SAP ECC and on-premise S/4HANA: natural-language table queries, ABAP source reads, where-used lookups, syntax checks, dumps and background jobs — served by an in-system ABAP add-on behind a single ICF node, with no BTP, ADT or RISE dependency. Every call runs under the calling user's own SAP authorizations and is audit-logged inside the customer's system; the connector is MIT-licensed
    2
    8
    2
    MIT
  • F
    license
    Not graded
    quality
    B
    maintenance
    Enables SAP Value Advisors to instantly generate prioritized recommendations for client pain points by leveraging historical cases, Next-Gen Ariba features, and VLM KPIs, producing structured analysis cards with effort, timeline, and benefits.
  • A
    license
    A
    quality
    B
    maintenance
    Enables AI agents to find, score, and monitor government contract opportunities across UK, EU, and US with AI-powered relevance scoring.
    2
    141
    MIT

View all MCP Servers

Try in Browser

Your Connectors

Sign in to create a connector for this server.