{"$schema":"https://wellknown.network/schemas/agent-record-v1.json","schemaVersion":"1","id":"ag_pb6atuzhc5fd","handle":"shotpulled","url":"https://wellknown.network/agents/shotpulled","links":{"self":"https://wellknown.network/agents/shotpulled/record.json","html":"https://wellknown.network/agents/shotpulled","markdown":"https://wellknown.network/agents/shotpulled/record.md","api":"https://wellknown.network/api/v1/agents/shotpulled","status":"https://wellknown.network/api/v1/agents/shotpulled/status","claim":"https://wellknown.network/agents/shotpulled/claim","claimApi":"https://wellknown.network/api/v1/claims","claimDescriptor":"https://wellknown.network/agents/shotpulled/claim.json","badge":"https://wellknown.network/agents/shotpulled/badge.svg","openapi":"https://wellknown.network/openapi.json","history":"https://wellknown.network/api/v1/agents/shotpulled/history","tools":"https://wellknown.network/api/v1/agents/shotpulled/tools"},"ard":{"identifier":"urn:air:mcp.shotpulled.com:server:shotpulled","type":"application/mcp-server-card+json"},"kind":"mcp_server","declared":{"name":"ShotPulled","summary":"Espresso dialing: log a shot, say how it tasted, get one change in your grinder's own clicks.","description":"Espresso dialing: log a shot, say how it tasted, get one change in your grinder's own clicks.","publisher":{"name":"com.shotpulled","url":null},"homepage":"https://shotpulled.com","repository":null,"version":"1.3.7","license":null,"protocols":["mcp"],"tags":[],"pricing":null,"endpoints":[{"url":"https://mcp.shotpulled.com/mcp","type":"mcp_streamable_http","auth":null,"probeable":true}],"skills":null,"tools":null,"extra":{"updatedAt":"2026-10-04T14:03:58.405943Z","publishedAt":"2026-10-04T14:03:58.405943Z","registryName":"com.shotpulled/shotpulled"},"attribution":{"kind":"mcp_registry","name":"mcp_registry","summary":"mcp_registry","version":"mcp_registry","description":"mcp_registry","homepageUrl":"mcp_registry","publisherName":"mcp_registry"}},"derived":{"capabilities":[{"slug":"geo.maps","name":"Maps & Places","confidence":0.554,"provenance":"derived"},{"slug":"dev.docs-lookup","name":"Documentation Lookup","confidence":0.54,"provenance":"derived"},{"slug":"knowledge.reasoning","name":"Reasoning & Planning","confidence":0.54,"provenance":"derived"},{"slug":"code.execution","name":"Code Execution","confidence":0.51,"provenance":"derived"}],"categories":["code","dev","geo","knowledge"],"language":"en"},"observed":{"status":"live","statusReason":"Responded 6h ago.","lastOkAt":"2026-10-09T19:27:19.116Z","lastProbedAt":"2026-10-09T19:27:19.116Z","statusComputedAt":"2026-10-09T19:28:28.247Z","reliability30d":{"probes":108,"successRate":1,"p50Ms":72,"basis":"service","measures":{"availability":"availability","latency":"response time","tools":"tool surface observed","summary":"Checks reached the service itself."},"checks":{"total":107,"ok":107,"authBoundaryOk":0,"serviceOk":107,"note":"Counted from the observation rows for the window, checks of the server only (HTTP, A2A card, MCP initialize). ok = authBoundaryOk + serviceOk. `probes` is the sum of daily rollups and includes registry checks, so it can differ from `total`."}},"latestObservations":[{"at":"2026-10-09T19:27:19.116Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":124,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-09T13:29:35.305Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":129,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-09T06:21:25.688Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":53,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-08T23:23:00.756Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":64,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-08T16:28:39.163Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":103,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-08T09:23:47.693Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":52,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-08T03:24:20.466Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":68,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-07T20:29:51.773Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":80,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-07T13:27:01.432Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":95,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}},{"at":"2026-10-07T07:26:41.607Z","kind":"mcp_initialize","ok":true,"httpStatus":200,"latencyMs":50,"error":null,"detail":{"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"toolCount":44,"toolsHash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","serverName":"shotpulled","capabilities":["logging","completions","prompts","resources","tools"],"serverVersion":"1.3.7","protocolVersion":"2025-06-18"}}],"tools":[{"name":"register_grinder","description":"Register a manual or electric grinder with its dial settings scheme. It becomes the active grinder only when no grinder is in use (none active, or the active on"},{"name":"set_grinder_position","description":"Set the current grinder collar position. source=\"measured\" resets verification freshness. It replaces the stored position; no history of earlier positions is ke"},{"name":"register_machine","description":"Register an espresso or alternative preparation machine. It becomes the active machine only when no machine is in use (none active, or the active one archived);"},{"name":"set_equipment_archived","description":"Archive or restore a grinder, machine, water, or scale."},{"name":"update_grinder","description":"Correct a registered grinder — its name, burrs, collar scheme, nominal step, layout, range or notes. Only the keys you send in fields change; send null to clear"},{"name":"update_machine","description":"Correct a registered machine — its name, control type, prep type and style, basket, boiler, accessories or notes — or record where its selectors stand (settings"},{"name":"update_scale","description":"Correct a registered scale — its type, resolution, capacity, capabilities, build or notes. Only the keys you send in fields change; send null to clear an option"},{"name":"update_water","description":"Correct a registered water — its name, type, mineral figures or notes. Only the keys you send in fields change; send null to clear an optional field (an empty s"},{"name":"log_maintenance","description":"Log a cleaning or maintenance job against a piece of equipment. A task that takes the thing apart opens a calibration epoch, and every recipe locked before it i"},{"name":"set_maintenance_offset","description":"Record how far a maintenance job moved the reference, on an entry that opened a calibration epoch. Takes an ENTRY, not a piece of equipment: the offset belongs "},{"name":"set_maintenance_schedule","description":"Set the user's own schedule for one maintenance task on one grinder or machine: their own interval, switching it off, or muting the reminder until a date. Only "},{"name":"get_maintenance_guides","description":"Step-by-step maintenance guides — tools, supplies, steps and warnings, in our own words with the maker's documents as sources. With no arguments, every guide fo"},{"name":"list_maintenance_due","description":"What maintenance is due across the user's current grinders and machines, most urgent first — for \"is anything due?\". Only tasks with an interval compete: a task"},{"name":"register_water","description":"Register a custom or commercial water formulation."},{"name":"list_waters","description":"List registered waters for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_scale","description":"Register a brewing scale — the instrument that weighs the dose and the yield."},{"name":"list_scales","description":"List registered scales for the account. The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, and what other too"},{"name":"register_program","description":"Register a programmed shot button on a machine. A program cuts the shot off either by weight (program_type \"volumetric\", set target_volume_g) or by time (progra"},{"name":"register_coffee","description":"Register a coffee that is NOT yet in list_beans, together with its first bag. It does not switch a coffee in use: it becomes active only when no coffee is in us"},{"name":"set_active","description":"Switch the active bean, grinder or machine for this account. The numbers come from list_beans, list_grinders and list_machines. Registering a coffee, grinder or"},{"name":"update_bean","description":"Update a coffee's own fields (roaster, origins, roast level, rest window, notes, rating…). Bag-shaped fields sent here (state, roast_date, bag_weight_g, grams_r"},{"name":"get_dial_state","description":"Retrieve current dialing state, active context, recent shots, recommendations, and locked recipes."},{"name":"log_shot","description":"Log an espresso or alternative shot/brew attempt. Uses the active context (bean/grinder/machine/program) unless overridden via bean_id/grinder_id/machine_id/pro"},{"name":"lock_recipe","description":"Lock a successful shot as the reference dialing recipe for this equipment profile. It overwrites the recipe already locked for the same coffee, grinder, machine"},{"name":"delete_shot","description":"Delete a logged shot from history. Restores the bean's remaining weight (which is derived from logged doses). Hard delete — there is no undo. To fix a mistake o"},{"name":"update_shot","description":"Correct fields on an already-logged shot in place — no need to delete and re-log. Use for fixing a wrong dose/yield/time or grind label, re-filing a shot onto t"},{"name":"list_recipes","description":"List recipes (all or filtered by equipment and status). The `id` on each row is the number this account knows that record by, counting from 1 — safe to show, an"},{"name":"get_stats","description":"Get compact flat usage stats for a grinder, machine, or bean."},{"name":"list_grinders","description":"List grinders registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_machines","description":"List machines registered for the account, with status filter. The `id` on each row is the number this account knows that record by, counting from 1 — safe to sh"},{"name":"list_beans","description":"List the coffees registered for the account, with status filter. Each coffee carries its bags[] (every purchase, with its own freshness and grams left) and curr"},{"name":"grinder_math","description":"Determine steps/clicks difference and directions between setting labels (C3)."},{"name":"compute_age","description":"Compute a bag's age in days off roast and its resting/staling verdict — the coffee's current bag by default, or the bag named."},{"name":"diagnose_shot","description":"Evaluate shot metrics to provide ranked hypotheses (C6) and warn on flip-flops (G2) or fatigue (G6). Resolves the SHOT's own bean — age computed at the shot's p"},{"name":"suggest_next_step","description":"Retrieve the single next experiment step from the reasoning engine."},{"name":"log_recommendation","description":"Log a recommended dialing change to allow contradiction/oscillation checking (G2)."},{"name":"get_rule","description":"Retrieve the detailed text of a specific rule from the knowledge base by its rule ID."},{"name":"get_kb_version","description":"Retrieve the current version of the knowledge base."},{"name":"kb_changelog","description":"Retrieve the changelog showing updates and version differences for the knowledge base."},{"name":"diagnose_preview","description":"Sandbox-only diagnosis, writes nothing (no verdict, no recommendation-trail entry). Two modes: pass shot_id to dry-run a LOGGED shot (optionally overriding its "},{"name":"list_shots","description":"List shot history with support for pagination and filtering. Every shot carries a derived taste_pending flag (1 = logged with no sensory tags, no rating, and no"},{"name":"register_bag","description":"Register another bag of a coffee that is already in list_beans — the same roaster's product, bought again. It keeps the coffee's recipes, notes and history; onl"},{"name":"update_bag","description":"Change bag-level facts on one bag of a coffee: open, seal, freeze, thaw or finish it, correct its roast date, weight, grams left or price. Bag numbers come from"},{"name":"merge_beans","description":"Fold one coffee into another when the same coffee was registered twice. Every bag, shot, recipe and recommendation of from_bean_id moves to into_bean_id; the ac"}],"package":null,"toolSurface":{"id":"ts_htv79365qwrk","endpointId":"ep_3gwhh5xckv4w","hash":"79debb169fcaca2428dbf944e6f9cb9372e434cb77933d66dbe8ee7f4c443976","toolCount":44,"serverName":"shotpulled","serverVersion":"1.3.7","protocolVersion":"2025-06-18","firstSeenAt":"2026-10-04T18:26:22.963Z","lastSeenAt":"2026-10-09T19:27:19.112Z","observations":19,"toolNames":["register_grinder","set_grinder_position","register_machine","set_equipment_archived","update_grinder","update_machine","update_scale","update_water","log_maintenance","set_maintenance_offset","set_maintenance_schedule","get_maintenance_guides","list_maintenance_due","register_water","list_waters","register_scale","list_scales","register_program","register_coffee","set_active","update_bean","get_dial_state","log_shot","lock_recipe","delete_shot","update_shot","list_recipes","get_stats","list_grinders","list_machines","list_beans","grinder_math","compute_age","diagnose_shot","suggest_next_step","log_recommendation","get_rule","get_kb_version","kb_changelog","diagnose_preview","list_shots","register_bag","update_bag","merge_beans"],"distinctSurfaces":10},"endpointFacts":[{"id":"ep_3gwhh5xckv4w","url":"https://mcp.shotpulled.com/mcp","type":"mcp_streamable_http","factsCheckedAt":"2026-10-09T13:29:35.330Z","auth":{"observedAt":"2026-10-09T13:29:35.418Z","authRequired":false,"scheme":null,"resourceMetadata":null,"authorizationServer":null,"conformance":{"dpop":false,"rfc8414":false,"rfc9728":false,"pkceS256":false,"clientIdMetadataDocument":false,"dynamicClientRegistration":false}},"tls":{"observedAt":"2026-10-09T13:29:35.453Z","protocol":"TLSv1.3","chainValid":true,"chainError":null,"hostMatches":true,"subject":"shotpulled.com","issuer":{"commonName":"WE1","organization":"Google Trust Services"},"validFrom":"2026-10-02T18:28:51.000Z","validTo":"2026-12-31T19:28:46.000Z","daysToExpiry":82,"sanCount":2,"fingerprint256":"05:B7:66:39:33:02:8D:FE:E3:08:45:5F:6F:FA:C4:FE:01:7D:5A:7F:B9:37:9D:E9:7E:86:20:1E:1E:F1:02:A2"}}]},"verification":{"claimed":false,"claimedAt":null,"proofs":[]},"provenance":{"sources":[{"source":"mcp_registry","key":"com.shotpulled/shotpulled","url":"https://registry.modelcontextprotocol.io/v0/servers/com.shotpulled%2Fshotpulled","firstSeenAt":"2026-09-05T21:20:36.510Z","fetchedAt":"2026-10-09T11:22:16.248Z","normalizedAt":"2026-10-09T11:22:16.248Z"}]},"firstSeenAt":"2026-09-05T21:20:36.510Z","updatedAt":"2026-10-09T19:29:34.524Z"}