{"serverId":"mcp-registry/io.github.benkaiser/mob-demo","tools":[{"name":"activity_list","fixed":{"name":"activity_list","description":"List activities, optionally filtered by contact or type. Add days_back or since for a chronological activity journal with participant names.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"page":{"type":"number","description":"Page number (default: 1)"},"type":{"enum":["phone_call","video_call","text_message","in_person","email","activity","other"],"type":"string","description":"Filter by interaction type"},"since":{"type":"string","description":"Show activities since this ISO date (uses activity log mode with participant names)"},"per_page":{"type":"number","description":"Results per page (default: 20)"},"days_back":{"type":"number","maximum":365,"minimum":1,"description":"Look-back window in days (uses activity log mode with participant names). Ignored if since is provided."},"contact_id":{"type":"string","description":"Filter by contact ID"},"sort_order":{"enum":["asc","desc"],"type":"string","description":"Sort direction by occurred_at (default: desc, only for activity log mode)"},"include_deleted":{"type":"boolean","description":"Include soft-deleted activities in results (default: false)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":335,"tokensAfter":335},{"name":"address_manage","fixed":{"name":"address_manage","description":"Add, update, or remove an address for a contact","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["action"],"properties":{"id":{"type":"string","description":"The address ID (required for \"update\" and \"remove\")"},"city":{"type":"string","description":"City"},"label":{"type":"string","description":"Label (e.g. \"Home\", \"Work\")"},"action":{"enum":["add","update","remove"],"type":"string","description":"Action to perform"},"country":{"type":"string","description":"Country (ISO 3166-1 alpha-2 recommended)"},"contact_id":{"type":"string","description":"The contact ID (required for \"add\")"},"is_primary":{"type":"boolean","description":"Set as primary address"},"postal_code":{"type":"string","description":"Postal/ZIP code"},"street_line_1":{"type":"string","description":"Street address line 1"},"street_line_2":{"type":"string","description":"Street address line 2"},"state_province":{"type":"string","description":"State or province"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":289,"tokensAfter":289},{"name":"batch_create_activities","fixed":{"name":"batch_create_activities","description":"Create multiple activities/interactions in one call. Max 50 items per batch. Runs atomically - if any item fails, the entire batch is rolled back.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["activities"],"properties":{"activities":{"type":"array","items":{"type":"object","required":["type","occurred_at","participant_contact_ids"],"properties":{"type":{"enum":["phone_call","video_call","text_message","in_person","email","activity","other"],"type":"string","description":"Type of interaction"},"title":{"type":"string","description":"Title (e.g. \"Coffee at Blue Bottle\")"},"location":{"type":"string","description":"Where it happened"},"description":{"type":"string","description":"Description or notes"},"occurred_at":{"type":"string","description":"When it happened (ISO date/datetime)"},"activity_type_id":{"type":"string","description":"Custom activity type ID"},"duration_minutes":{"type":"number","description":"Duration in minutes"},"participant_contact_ids":{"type":"array","items":{"type":"string"},"description":"Contact IDs of participants"}}},"description":"Array of activity creation inputs (max 50)"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":340,"tokensAfter":340},{"name":"batch_create_contacts","fixed":{"name":"batch_create_contacts","description":"Create multiple contacts in one call. Max 50 items per batch. Runs atomically - if any item fails, the entire batch is rolled back.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contacts"],"properties":{"contacts":{"type":"array","items":{"type":"object","required":["first_name"],"properties":{"gender":{"type":"string","description":"Gender"},"status":{"enum":["active","archived","deceased"],"type":"string","description":"Contact status (default: active)"},"company":{"type":"string","description":"Company or organization"},"industry":{"type":"string","description":"Industry"},"nickname":{"type":"string","description":"Nickname"},"pronouns":{"type":"string","description":"Pronouns (e.g. she/her, he/him, they/them)"},"job_title":{"type":"string","description":"Job title"},"last_name":{"type":"string","description":"Last name"},"avatar_url":{"type":"string","description":"Avatar URL"},"first_name":{"type":"string","description":"First name (required)"},"work_notes":{"type":"string","description":"Notes about their work"},"is_favorite":{"type":"boolean","description":"Mark as favorite"},"maiden_name":{"type":"string","description":"Maiden name"},"met_at_date":{"type":"string","description":"Date you met this person (YYYY-MM-DD)"},"middle_name":{"type":"string","description":"Middle name"},"birthday_day":{"type":"number","description":"Birthday day (1-31), used with birthday_mode=month_day"},"birthday_date":{"type":"string","description":"Full birthday date (YYYY-MM-DD), used with birthday_mode=full_date"},"birthday_mode":{"enum":["full_date","month_day","approximate_age"],"type":"string","description":"Birthday mode: full_date (YYYY-MM-DD), month_day (month + day only), or approximate_age (birth year estimate)"},"deceased_date":{"type":"string","description":"Date of death (YYYY-MM-DD)"},"birthday_month":{"type":"number","description":"Birthday month (1-12), used with birthday_mode=month_day"},"met_at_location":{"type":"string","description":"Where you met this person"},"met_description":{"type":"string","description":"Story of how you met"},"met_through_contact_id":{"type":"string","description":"Contact ID of person who introduced you"},"birthday_year_approximate":{"type":"number","description":"Approximate birth year, used with birthday_mode=approximate_age"}}},"description":"Array of contact creation inputs (max 50)"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":684,"tokensAfter":684},{"name":"contact_create","fixed":{"name":"contact_create","description":"Create a new contact with basic info","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["first_name"],"properties":{"gender":{"type":"string","description":"Gender"},"status":{"enum":["active","archived","deceased"],"type":"string","description":"Contact status (default: active)"},"company":{"type":"string","description":"Company or organization"},"industry":{"type":"string","description":"Industry"},"nickname":{"type":"string","description":"Nickname"},"pronouns":{"type":"string","description":"Pronouns (e.g. she/her, he/him, they/them)"},"job_title":{"type":"string","description":"Job title"},"last_name":{"type":"string","description":"Last name"},"avatar_url":{"type":"string","description":"Avatar URL"},"first_name":{"type":"string","description":"First name (required)"},"work_notes":{"type":"string","description":"Notes about their work"},"is_favorite":{"type":"boolean","description":"Mark as favorite"},"maiden_name":{"type":"string","description":"Maiden name"},"met_at_date":{"type":"string","description":"Date you met this person (YYYY-MM-DD)"},"middle_name":{"type":"string","description":"Middle name"},"birthday_day":{"type":"number","description":"Birthday day (1-31), used with birthday_mode=month_day"},"birthday_date":{"type":"string","description":"Full birthday date (YYYY-MM-DD), used with birthday_mode=full_date"},"birthday_mode":{"enum":["full_date","month_day","approximate_age"],"type":"string","description":"Birthday mode: full_date (YYYY-MM-DD), month_day (month + day only), or approximate_age (birth year estimate)"},"deceased_date":{"type":"string","description":"Date of death (YYYY-MM-DD)"},"birthday_month":{"type":"number","description":"Birthday month (1-12), used with birthday_mode=month_day"},"met_at_location":{"type":"string","description":"Where you met this person"},"met_description":{"type":"string","description":"Story of how you met"},"met_through_contact_id":{"type":"string","description":"Contact ID of person who introduced you"},"birthday_year_approximate":{"type":"number","description":"Approximate birth year, used with birthday_mode=approximate_age"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":614,"tokensAfter":614},{"name":"contact_delete","fixed":{"name":"contact_delete","description":"Soft-delete a contact (can be restored later)","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contact_id"],"properties":{"contact_id":{"type":"string","description":"The contact ID to delete"}}},"annotations":{"readOnlyHint":false,"destructiveHint":true,"idempotentHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: true, idempotentHint: true (inferred from the name).","verify":true}],"tokensBefore":79,"tokensAfter":79},{"name":"contact_find_duplicates","fixed":{"name":"contact_find_duplicates","description":"Scan for potential duplicate contacts using name, email, and phone matching. Returns pairs of contacts that may be duplicates with the reason for the match.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":86,"tokensAfter":86},{"name":"contact_get","fixed":{"name":"contact_get","description":"Get full contact details including all related data in one call: contact methods, addresses, food preferences, custom fields, tags, relationships, recent notes, recent activities, life events, active reminders, open tasks, recent gifts, active debts, and debt summary","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contact_id"],"properties":{"contact_id":{"type":"string","description":"The contact ID"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":137,"tokensAfter":137},{"name":"contact_list","fixed":{"name":"contact_list","description":"List contacts with optional filters (status, favorite, company, tag, search). Returns paginated results.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"page":{"type":"number","description":"Page number (default: 1)"},"search":{"type":"string","description":"Search contacts by name, company, or job title"},"status":{"enum":["active","archived","deceased"],"type":"string","description":"Filter by status"},"company":{"type":"string","description":"Filter by company"},"sort_by":{"enum":["name","created_at","updated_at"],"type":"string","description":"Sort field (default: name)"},"per_page":{"type":"number","description":"Results per page (default: 20)"},"tag_name":{"type":"string","description":"Filter by tag name"},"sort_order":{"enum":["asc","desc"],"type":"string","description":"Sort order (default: asc)"},"is_favorite":{"type":"boolean","description":"Filter by favorite"},"include_deleted":{"type":"boolean","description":"Include soft-deleted contacts in results (default: false)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":303,"tokensAfter":303},{"name":"contact_merge","fixed":{"name":"contact_merge","description":"Merge two contacts into one. All child records (notes, activities, tags, etc.) from the secondary contact are moved to the primary. The secondary contact is soft-deleted after merge.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["primary_contact_id","secondary_contact_id"],"properties":{"primary_contact_id":{"type":"string","description":"The contact ID to keep (primary)"},"secondary_contact_id":{"type":"string","description":"The contact ID to merge into the primary (will be soft-deleted)"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":164,"tokensAfter":164},{"name":"contact_update","fixed":{"name":"contact_update","description":"Update contact fields","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contact_id"],"properties":{"gender":{"type":"string","description":"Gender"},"status":{"enum":["active","archived","deceased"],"type":"string","description":"Contact status"},"company":{"type":"string","description":"Company"},"industry":{"type":"string","description":"Industry"},"nickname":{"type":"string","description":"Nickname"},"pronouns":{"type":"string","description":"Pronouns"},"job_title":{"type":"string","description":"Job title"},"last_name":{"type":"string","description":"Last name"},"avatar_url":{"type":"string","description":"Avatar URL"},"contact_id":{"type":"string","description":"The contact ID to update"},"first_name":{"type":"string","description":"First name"},"work_notes":{"type":"string","description":"Work notes"},"is_favorite":{"type":"boolean","description":"Mark as favorite"},"maiden_name":{"type":"string","description":"Maiden name"},"met_at_date":{"type":"string","description":"Date you met this person"},"middle_name":{"type":"string","description":"Middle name"},"birthday_day":{"type":"number","description":"Birthday day (1-31)"},"birthday_date":{"type":"string","description":"Full birthday date (YYYY-MM-DD)"},"birthday_mode":{"enum":["full_date","month_day","approximate_age"],"type":"string","description":"Birthday mode"},"deceased_date":{"type":"string","description":"Date of death (YYYY-MM-DD)"},"birthday_month":{"type":"number","description":"Birthday month (1-12)"},"met_at_location":{"type":"string","description":"Where you met this person"},"met_description":{"type":"string","description":"How you met"},"met_through_contact_id":{"type":"string","description":"Contact ID of person who introduced you"},"birthday_year_approximate":{"type":"number","description":"Approximate birth year"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: true (inferred from the name).","verify":true}],"tokensBefore":531,"tokensAfter":531},{"name":"data_export","fixed":{"name":"data_export","description":"Export all CRM data as a JSON object (contacts, relationships, notes, activities, life events, reminders, gifts, debts, tasks, tags)","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":76,"tokensAfter":76},{"name":"food_preferences_get","fixed":{"name":"food_preferences_get","description":"Get food preferences for a contact (dietary restrictions, allergies, favorites, dislikes)","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contact_id"],"properties":{"contact_id":{"type":"string","description":"The contact ID"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":90,"tokensAfter":90},{"name":"food_preferences_upsert","fixed":{"name":"food_preferences_upsert","description":"Set or update food preferences for a contact. Replaces all fields - pass all known preferences, not just changes.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["contact_id"],"properties":{"notes":{"type":"string","description":"Additional notes about food preferences"},"allergies":{"type":"array","items":{"type":"string"},"description":"Food allergies (e.g. [\"peanuts\", \"shellfish\"])"},"contact_id":{"type":"string","description":"The contact ID"},"disliked_foods":{"type":"array","items":{"type":"string"},"description":"Disliked foods"},"favorite_foods":{"type":"array","items":{"type":"string"},"description":"Favorite foods"},"dietary_restrictions":{"type":"array","items":{"type":"string"},"description":"Dietary restrictions (e.g. [\"vegetarian\", \"gluten-free\"])"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: true (inferred from the name).","verify":true}],"tokensBefore":245,"tokensAfter":245},{"name":"gift_list","fixed":{"name":"gift_list","description":"List gifts, optionally filtered by contact, status, or direction. Add occasion, sort_by, sort_order, or omit contact_id for a cross-contact gift tracker with summary stats.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"page":{"type":"number","description":"Page number (default: 1)"},"status":{"enum":["idea","planned","purchased","given","received"],"type":"string","description":"Filter by status"},"sort_by":{"enum":["date","created_at","estimated_cost"],"type":"string","description":"Sort field (default: date for tracker mode, created_at otherwise)"},"occasion":{"type":"string","description":"Filter by occasion (fuzzy match, e.g. \"birthday\", \"Christmas\")"},"per_page":{"type":"number","description":"Results per page (default: 20)"},"direction":{"enum":["giving","receiving"],"type":"string","description":"Filter by direction"},"contact_id":{"type":"string","description":"Filter by contact ID"},"sort_order":{"enum":["asc","desc"],"type":"string","description":"Sort direction (default: desc)"},"include_deleted":{"type":"boolean","description":"Include soft-deleted gifts in results (default: false)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":336,"tokensAfter":336},{"name":"global_search","fixed":{"name":"global_search","description":"Search across all entity types (contacts, notes, activities, life events, gifts, tasks, reminders, debts, relationships, contact methods, addresses, custom fields) in a single query. Returns grouped results by entity type with snippets and contact context.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["query"],"properties":{"query":{"type":"string","description":"Search term"},"entity_types":{"type":"array","items":{"enum":["contacts","notes","activities","life_events","gifts","tasks","reminders","debts","relationships","contact_methods","addresses","custom_fields"],"type":"string"},"description":"Optional: filter to specific entity types (default: all types)"},"limit_per_type":{"type":"number","maximum":50,"minimum":1,"description":"Max results per entity type (default: 10)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":245,"tokensAfter":245},{"name":"manage_settings","fixed":{"name":"manage_settings","description":"View or update your personal settings (timezone, birthday reminder preferences).\n• action=\"get\": View current settings\n• action=\"update\": Update settings. Optional fields: timezone (IANA timezone like \"America/New_York\"), birthday_reminder_offsets (array of day offsets like [0,7,30] where 0=day-of, 7=week-before), reminder_offsets (array of day offsets like [0,7,30] for advance notice on custom reminders), birthday_reminder_time (HH:MM 24-hour format for when to send reminders)","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["action"],"properties":{"action":{"enum":["get","update"],"type":"string","description":"Action to perform"},"timezone":{"type":"string","description":"IANA timezone (e.g. \"America/New_York\", \"Europe/London\")"},"reminder_offsets":{"type":"array","items":{"type":"number"},"description":"Array of day offsets for custom reminder advance notice (e.g. [0,7,30] = day-of, 1 week before, 1 month before)"},"birthday_reminder_time":{"type":"string","description":"Time of day for birthday reminders in HH:MM 24-hour format (e.g. \"09:00\")"},"birthday_reminder_offsets":{"type":"array","items":{"type":"number"},"description":"Array of day offsets for birthday reminders (e.g. [0,7,30] = day-of, 1 week before, 1 month before)"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: true (inferred from the name).","verify":true}],"tokensBefore":377,"tokensAfter":377},{"name":"note_list","fixed":{"name":"note_list","description":"List and search notes. When contact_id is provided alone, lists that contact's notes (pinned first). Add query, tag_name, is_pinned, or omit contact_id to search across all contacts.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"page":{"type":"number","description":"Page number (default: 1)"},"query":{"type":"string","description":"Search term matched against note title and body"},"sort_by":{"enum":["created_at","updated_at"],"type":"string","description":"Sort field (default: updated_at)"},"per_page":{"type":"number","description":"Results per page (default: 20)"},"tag_name":{"type":"string","description":"Filter to notes belonging to contacts with this tag"},"is_pinned":{"type":"boolean","description":"Filter by pinned status"},"contact_id":{"type":"string","description":"Filter by contact ID (optional - omit to search across all contacts)"},"sort_order":{"enum":["asc","desc"],"type":"string","description":"Sort direction (default: desc)"},"include_deleted":{"type":"boolean","description":"Include soft-deleted notes in results (default: false)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":321,"tokensAfter":321},{"name":"notification_create","fixed":{"name":"notification_create","description":"Create a custom notification","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","required":["type","title"],"properties":{"body":{"type":"string","description":"Notification body"},"type":{"enum":["birthday","reminder","follow_up","custom"],"type":"string","description":"Notification type"},"title":{"type":"string","description":"Notification title"},"contact_id":{"type":"string","description":"Related contact ID"}}},"annotations":{"readOnlyHint":false,"destructiveHint":false,"idempotentHint":false}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: false, destructiveHint: false, idempotentHint: false (inferred from the name).","verify":true}],"tokensBefore":139,"tokensAfter":139},{"name":"notification_list","fixed":{"name":"notification_list","description":"List notifications (newest first)","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"page":{"type":"number","description":"Page number (default: 1)"},"per_page":{"type":"number","description":"Results per page (default: 20)"},"unread_only":{"type":"boolean","description":"Only show unread notifications"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":111,"tokensAfter":111},{"name":"notification_read","fixed":{"name":"notification_read","description":"Mark notification(s) as read. Pass id for a single notification, or all=true for all.","inputSchema":{"type":"object","$schema":"http://json-schema.org/draft-07/schema#","properties":{"id":{"type":"string","description":"The notification ID (required unless all=true)"},"all":{"type":"boolean","description":"Mark all notifications as read (default: false)"}}},"annotations":{"readOnlyHint":true}},"changes":[{"kind":"annotations","detail":"Added readOnlyHint: true (inferred from the name).","verify":true}],"tokensBefore":113,"tokensAfter":113}],"toolsChanged":21,"tokensSaved":0,"todo":[],"note":"Deterministic fixes. Changes marked verify need a human look before shipping (renames, inferred annotations, inferred types, removed text). Parameter descriptions in `todo` need to be written by someone who knows the API."}