> ## Documentation Index
> Fetch the complete documentation index at: https://docs.mavera.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Meeting Notes → Mave Research

> Aggregate HubSpot meeting notes and synthesize themes, objections, and competitive mentions with Mave

## Scenario

Your sales team logs meeting notes in HubSpot after every prospect call. After 20+ meetings, patterns emerge — same objections, feature requests, competitive mentions — but nobody synthesizes them. You aggregate notes and send them to Mave for theme analysis and recommendations.

## Architecture

```mermaid theme={"dark"}
flowchart LR
    A[HubSpot Meetings Search] --> B[Aggregate notes] --> C["POST /mave/chat"] --> D[Theme synthesis]
```

## Code

<CodeGroup>
  ```python Python theme={"dark"}
  import os, requests, time

  HS = os.environ["HUBSPOT_ACCESS_TOKEN"]
  MV = os.environ["MAVERA_API_KEY"]

  # 1. Pull recent meetings
  r = requests.post("https://api.hubapi.com/crm/v3/objects/meetings/search",
      headers={"Authorization": f"Bearer {HS}"},
      json={
          "filterGroups": [{"filters": [{"propertyName": "hs_meeting_outcome", "operator": "HAS_PROPERTY"}]}],
          "properties": ["hs_meeting_title", "hs_meeting_body", "hs_internal_meeting_notes", "hs_meeting_outcome"],
          "sorts": [{"propertyName": "hs_meeting_start_time", "direction": "DESCENDING"}],
          "limit": 25,
      })
  if r.status_code == 429: time.sleep(1)
  r.raise_for_status()
  meetings = r.json().get("results", [])

  # 2. Aggregate notes
  notes = []
  for m in meetings:
      p = m.get("properties", {})
      body = p.get("hs_internal_meeting_notes") or p.get("hs_meeting_body") or ""
      if body.strip():
          notes.append(f"Meeting: {p.get('hs_meeting_title','Untitled')}\nOutcome: {p.get('hs_meeting_outcome','')}\n{body[:500]}")

  block = "\n\n---\n\n".join(notes[:20])

  # 3. Mave synthesis
  mave = requests.post("https://app.mavera.io/api/v1/mave/chat",
      headers={"Authorization": f"Bearer {MV}", "Content-Type": "application/json"},
      json={"message": f"""Synthesize key themes, objections, competitive mentions, and feature requests
  from these {len(notes)} prospect meetings.

  For each theme: frequency, representative quotes, strategic recommendation.
  Top 3 objections with suggested responses. Competitive products mentioned.

  {block}"""}).json()

  print("--- Meeting Intelligence ---")
  print(mave.get("content", "")[:2000])
  ```

  ```javascript JavaScript theme={"dark"}
  const HS = process.env.HUBSPOT_ACCESS_TOKEN;
  const MV = process.env.MAVERA_API_KEY;

  // 1. Pull meetings
  const meetings = await fetch("https://api.hubapi.com/crm/v3/objects/meetings/search", {
    method: "POST",
    headers: { Authorization: `Bearer ${HS}`, "Content-Type": "application/json" },
    body: JSON.stringify({
      filterGroups: [{ filters: [{ propertyName: "hs_meeting_outcome", operator: "HAS_PROPERTY" }] }],
      properties: ["hs_meeting_title", "hs_meeting_body", "hs_internal_meeting_notes", "hs_meeting_outcome"],
      sorts: [{ propertyName: "hs_meeting_start_time", direction: "DESCENDING" }],
      limit: 25,
    }),
  }).then(r => r.json()).then(d => d.results || []);

  // 2. Aggregate
  const notes = meetings.map(m => {
    const p = m.properties || {};
    const body = p.hs_internal_meeting_notes || p.hs_meeting_body || "";
    return body.trim() ? `Meeting: ${p.hs_meeting_title || "Untitled"}\nOutcome: ${p.hs_meeting_outcome || ""}\n${body.slice(0, 500)}` : null;
  }).filter(Boolean);

  // 3. Mave synthesis
  const mave = await fetch("https://app.mavera.io/api/v1/mave/chat", {
    method: "POST",
    headers: { Authorization: `Bearer ${MV}`, "Content-Type": "application/json" },
    body: JSON.stringify({
      message: `Synthesize key themes, objections, competitive mentions from these ${notes.length} meetings.\n\n${notes.slice(0, 20).join("\n\n---\n\n")}`,
    }),
  }).then(r => r.json());

  console.log("--- Meeting Intelligence ---");
  console.log((mave.content || "").slice(0, 2000));
  ```
</CodeGroup>

## Example Output

```text theme={"dark"}
## Key Themes (20 meetings)
1. Data Integration Complexity (14/20) → Lead with native integrations list
2. Budget Timing (9/20) → Offer pilot pricing bridging to next fiscal year

## Top 3 Objections
1. "Locked into annual contract with [competitor]" (8x)
2. "No bandwidth to onboard another tool" (6x)
3. "How is this different from what we have?" (5x)
```

## Error Handling

<AccordionGroup>
  <Accordion title="Notes in different fields">HubSpot stores notes in `hs_internal_meeting_notes` or `hs_meeting_body`. The code checks both.</Accordion>
  <Accordion title="Context window limits">50+ meetings may exceed Mave's context. Code truncates to 500 chars each and caps at 20. Batch-summarize larger volumes.</Accordion>
</AccordionGroup>

***

<CardGroup cols={2}>
  <Card title="HubSpot Integration" icon="arrow-left" href="/integrations/hubspot" />

  <Card title="Mave Agent" icon="brain" href="/features/mave-agent" />
</CardGroup>
