Skip to main content
Glama

plan_factory

Solves factory plans with linear programming using unlocked recipes to optimize power, item output, raw resource use, machine counts, exports, and byproducts.

Instructions

Solve a factory plan by LP over this world's unlocked recipes: machines, rates, power, exports, byproducts.

sources= node selectors, combinable; omit = whole map: "north", "region:Northern Forest", "near:@<radius_m>", "node:" (search_resource_nodes lists ids), "grid:X3Y4", "resource:Crude Oil". objective: max_mw | max_item | min_raw | min_raw_power | min_machines | min_power. Omitted: min_raw_power when export_minimums asks for an item, else max_mw. Machine counts are whole buildings at one derived clock. exports= whitelist of what may leave, REPLACING the default (omitted: a goalless rate exports its items on grid power, else power only); [] = only export_minimums, grid power. Listing "MW" exports power and forbids grid draw: ["MW","Plastic"]. extractor_clocks overclocks source nodes only; clocks spreads a row over more, slower machines at machine_cost_mw each. Power Shards are not counted. required= recipes (exact name or class id) that must make their item, excluding their rivals; a locked one is refused. save_as= stores the request, never the solution; over an existing plan pass base_rev. plan= recalls a saved plan and re-solves it. Unsaved, the answer ends plan="solve:..." for the other plan tools (held until restart). site_at= with save_as records where the plan stands and measures the water there.

Input Schema

NameRequiredDescriptionDefault
planNorecall a saved plan (name or pin:N); other arguments override this call only
saveNo
as_ofNopin to one save: the sav:… token an earlier answer printed
limitNo
worldNo
clocksNoclock options for production rows, e.g. [0.5, 1.0]; omit = 1.0
sloopsNoSomersloops the plan may spend; 0 spends none
exportsNo
save_asNostore this request under a name
site_atNowith save_as: where the plan stands (footprint centre): 'x,y[,z]' in metres, 'me', a factory name, 'slab:<n>', 'chain:<n>'/'pipe:<n>'
sourcesNo
base_revNothe plan version you read; needed to save over an existing plan
overflowNo'sink': minimums exports omits are sunk, power from the grid
requiredNorecipes that must make their item; others for it are excluded
suppliedNoitems another plan hands this one, {item: per-minute}
objectiveNoomitted: min_raw_power with export_minimums, else max_mw
allow_sinksNo
for_factoryNofactory this plan is built at; also 'auto', 'whole world', 'none'
power_priceNopoints per MWh for payback pricing; omit = the save's grid mix; 'default' resets a saved plan to it
target_itemNothe item max_item maximises
only_recipesNo
recycle_onceNorecipes that may run but must not feed each other, e.g. ['Recycled']
site_yaw_degNosite orientation: degrees about world Z, positive +X towards +Y
payback_hoursNohours of play in which slower extra machines must repay their build points in saved power; 0 = plain build; stops 1, 2, 5, 10, 20, 50, 100; from 5 h, max_mw and min_power price machines at build points instead of machine_cost_mw; 'default' = shared setting
row_overclockNoper recipe (exact name or class id): 'last' overclocks the row's last machine, 'spread' adds one underclocked machine, 'default' follows overclock_last; unnamed rows keep their stored choice
overclock_lastNobuild each row one machine short, the last overclocked (1-2 Power Shards, checked against shards in hand plus craftable from slugs); 'default' = shared setting
site_footprintNo'WxD' in metres; blank = the layout's own square
exclude_recipesNo
export_minimumsNo{item: per-minute} minimum exports; the 'rate' request
logistics_itemsNoitems whose belt/pipe rows to pin, whatever their volume
machine_cost_mwNo
only_free_nodesNoskip nodes an extractor already taps
plan_notes_textNonote stored with save_as
extractor_clocksNoclock options for source nodes, e.g. [1.0, 1.5, 2.0, 2.5]
water_extractorsNohow many Water Extractors your site can actually hold

Schema Changelog

Changes observed during successful MCP inspections.

  1. Changed106 schema fields changedv0.3.0
    • removedInput schema / properties / allow_sinks / title
      Removed value: -"Allow Sinks"
    • removedInput schema / properties / as_of / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • changedInput schema / properties / as_of / description
      Previous value: -"pin to one world state: a sav:… token from an earlier answer"New value: +"pin to one save: the sav:… token an earlier answer printed"
    • removedInput schema / properties / as_of / title
      Removed value: -"As Of"
    • addedInput schema / properties / as_of / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / properties / base_rev / anyOf
      Removed value: -[
      -  {
      -    "type": "integer"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / base_rev / title
      Removed value: -"Base Rev"
    • addedInput schema / properties / base_rev / type
      Added value: +[
      +  "integer",
      +  "null"
      +]
    • removedInput schema / properties / clocks / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "number"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / clocks / description
      Added value: +"clock options for production rows, e.g. [0.5, 1.0]; omit = 1.0"
    • addedInput schema / properties / clocks / items
      Added value: +{
      +  "type": "number"
      +}
    • removedInput schema / properties / clocks / title
      Removed value: -"Clocks"
    • addedInput schema / properties / clocks / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • removedInput schema / properties / exclude_recipes / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / exclude_recipes / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / exclude_recipes / title
      Removed value: -"Exclude Recipes"
    • addedInput schema / properties / exclude_recipes / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • addedInput schema / properties / export_minimums / additionalProperties
      Added value: +{
      +  "type": "number"
      +}
    • removedInput schema / properties / export_minimums / anyOf
      Removed value: -[
      -  {
      -    "additionalProperties": {
      -      "type": "number"
      -    },
      -    "type": "object"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / export_minimums / description
      Added value: +"{item: per-minute} minimum exports; the 'rate' request"
    • removedInput schema / properties / export_minimums / title
      Removed value: -"Export Minimums"
    • addedInput schema / properties / export_minimums / type
      Added value: +[
      +  "object",
      +  "null"
      +]
    • removedInput schema / properties / exports / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / exports / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / exports / title
      Removed value: -"Exports"
    • addedInput schema / properties / exports / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • removedInput schema / properties / extractor_clocks / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "number"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / extractor_clocks / description
      Added value: +"clock options for source nodes, e.g. [1.0, 1.5, 2.0, 2.5]"
    • addedInput schema / properties / extractor_clocks / items
      Added value: +{
      +  "type": "number"
      +}
    • removedInput schema / properties / extractor_clocks / title
      Removed value: -"Extractor Clocks"
    • addedInput schema / properties / extractor_clocks / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • removedInput schema / properties / for_factory / title
      Removed value: -"For Factory"
    • removedInput schema / properties / limit / description
      Removed value: -"max rows (hard cap 25)"
    • removedInput schema / properties / limit / title
      Removed value: -"Limit"
    • removedInput schema / properties / logistics_items / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / logistics_items / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / logistics_items / title
      Removed value: -"Logistics Items"
    • addedInput schema / properties / logistics_items / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • removedInput schema / properties / machine_cost_mw / title
      Removed value: -"Machine Cost Mw"
    • removedInput schema / properties / objective / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / objective / title
      Removed value: -"Objective"
    • addedInput schema / properties / objective / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • addedInput schema / properties / only_free_nodes / description
      Added value: +"skip nodes an extractor already taps"
    • removedInput schema / properties / only_free_nodes / title
      Removed value: -"Only Free Nodes"
    • removedInput schema / properties / only_recipes / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / only_recipes / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / only_recipes / title
      Removed value: -"Only Recipes"
    • addedInput schema / properties / only_recipes / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • changedInput schema / properties / overclock_last / description
      Previous value: -"build a row one machine short, the last one overclocked (1-2 Power Shards, checked against shards in hand plus those craftable from slugs); 'default' follows the shared setting"New value: +"build each row one machine short, the last overclocked (1-2 Power Shards, checked against shards in hand plus craftable from slugs); 'default' = shared setting"
    • removedInput schema / properties / overclock_last / title
      Removed value: -"Overclock Last"
    • addedInput schema / properties / overflow
      Added value: +{
      +  "anyOf": [
      +    {
      +      "enum": [
      +        "export",
      +        "sink"
      +      ],
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "'sink': minimums exports omits are sunk, power from the grid"
      +}
    • changedInput schema / properties / payback_hours / description
      Previous value: -"hours of play extra, slower machines must repay in saved power: 0 builds plainly; stops 1, 2, 5, 10, 20, 50, 100; 'default' follows the shared setting. Stored per plan"New value: +"hours of play in which slower extra machines must repay their build points in saved power; 0 = plain build; stops 1, 2, 5, 10, 20, 50, 100; from 5 h, max_mw and min_power price machines at build points instead of machine_cost_mw; 'default' = shared setting"
    • removedInput schema / properties / payback_hours / title
      Removed value: -"Payback Hours"
    • removedInput schema / properties / plan / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • changedInput schema / properties / plan / description
      Previous value: -"recall a saved plan by name"New value: +"recall a saved plan (name or pin:N); other arguments override this call only"
    • removedInput schema / properties / plan / title
      Removed value: -"Plan"
    • addedInput schema / properties / plan / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / properties / plan_notes_text / title
      Removed value: -"Plan Notes Text"
    • changedInput schema / properties / power_price / description
      Previous value: -"points per MWh the horizon prices power at; omit for the save's grid mix, 'default' puts a stored plan back on it"New value: +"points per MWh for payback pricing; omit = the save's grid mix; 'default' resets a saved plan to it"
    • removedInput schema / properties / power_price / title
      Removed value: -"Power Price"
    • removedInput schema / properties / recycle_once / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / recycle_once / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / recycle_once / title
      Removed value: -"Recycle Once"
    • addedInput schema / properties / recycle_once / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • removedInput schema / properties / required / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / required / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / required / title
      Removed value: -"Required"
    • addedInput schema / properties / required / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • addedInput schema / properties / row_overclock / additionalProperties
      Added value: +{
      +  "enum": [
      +    "last",
      +    "spread",
      +    "default"
      +  ],
      +  "type": "string"
      +}
    • removedInput schema / properties / row_overclock / anyOf
      Removed value: -[
      -  {
      -    "additionalProperties": {
      -      "enum": [
      -        "last",
      -        "spread",
      -        "default"
      -      ],
      -      "type": "string"
      -    },
      -    "type": "object"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • changedInput schema / properties / row_overclock / description
      Previous value: -"per recipe (exact name or class id): 'last' overclocks that row's last machine, 'spread' builds one more underclocked machine instead, 'default' follows overclock_last again. Overrides overclock_last for that row; rows not named keep their stored choice"New value: +"per recipe (exact name or class id): 'last' overclocks the row's last machine, 'spread' adds one underclocked machine, 'default' follows overclock_last; unnamed rows keep their stored choice"
    • removedInput schema / properties / row_overclock / title
      Removed value: -"Row Overclock"
    • addedInput schema / properties / row_overclock / type
      Added value: +[
      +  "object",
      +  "null"
      +]
    • removedInput schema / properties / save / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / save / title
      Removed value: -"Save"
    • addedInput schema / properties / save / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / properties / save_as / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / save_as / title
      Removed value: -"Save As"
    • addedInput schema / properties / save_as / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / properties / site_at / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • changedInput schema / properties / site_at / description
      Previous value: -"with save_as: record where this plan will STAND -- 'x,y[,z]' in metres, 'me', a factory name, 'slab:<n>' or a run id (the footprint's centre)"New value: +"with save_as: where the plan stands (footprint centre): 'x,y[,z]' in metres, 'me', a factory name, 'slab:<n>', 'chain:<n>'/'pipe:<n>'"
    • removedInput schema / properties / site_at / title
      Removed value: -"Site At"
    • addedInput schema / properties / site_at / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • changedInput schema / properties / site_footprint / description
      Previous value: -"site footprint 'WxD' in metres; blank = the layout's own square"New value: +"'WxD' in metres; blank = the layout's own square"
    • removedInput schema / properties / site_footprint / title
      Removed value: -"Site Footprint"
    • removedInput schema / properties / site_yaw_deg / title
      Removed value: -"Site Yaw Deg"
    • removedInput schema / properties / sloops / title
      Removed value: -"Sloops"
    • removedInput schema / properties / sources / anyOf
      Removed value: -[
      -  {
      -    "items": {
      -      "type": "string"
      -    },
      -    "type": "array"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / sources / items
      Added value: +{
      +  "type": "string"
      +}
    • removedInput schema / properties / sources / title
      Removed value: -"Sources"
    • addedInput schema / properties / sources / type
      Added value: +[
      +  "array",
      +  "null"
      +]
    • addedInput schema / properties / supplied / additionalProperties
      Added value: +{
      +  "type": "number"
      +}
    • removedInput schema / properties / supplied / anyOf
      Removed value: -[
      -  {
      -    "additionalProperties": {
      -      "type": "number"
      -    },
      -    "type": "object"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / supplied / title
      Removed value: -"Supplied"
    • addedInput schema / properties / supplied / type
      Added value: +[
      +  "object",
      +  "null"
      +]
    • removedInput schema / properties / target_item / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • addedInput schema / properties / target_item / description
      Added value: +"the item max_item maximises"
    • removedInput schema / properties / target_item / title
      Removed value: -"Target Item"
    • addedInput schema / properties / target_item / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / properties / water_extractors / anyOf
      Removed value: -[
      -  {
      -    "type": "integer"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / water_extractors / title
      Removed value: -"Water Extractors"
    • addedInput schema / properties / water_extractors / type
      Added value: +[
      +  "integer",
      +  "null"
      +]
    • removedInput schema / properties / world / anyOf
      Removed value: -[
      -  {
      -    "type": "string"
      -  },
      -  {
      -    "type": "null"
      -  }
      -]
    • removedInput schema / properties / world / title
      Removed value: -"World"
    • addedInput schema / properties / world / type
      Added value: +[
      +  "string",
      +  "null"
      +]
    • removedInput schema / title
      Removed value: -"plan_factoryArguments"
  2. Changed9 schema fields changedv0.2.0
    • changedInput schema / properties / for_factory / description
      Previous value: -"factory label this plan is for"New value: +"factory this plan is built at; also 'auto', 'whole world', 'none'"
    • addedInput schema / properties / objective / anyOf
      Added value: +[
      +  {
      +    "type": "string"
      +  },
      +  {
      +    "type": "null"
      +  }
      +]
    • changedInput schema / properties / objective / default
      Previous value: -"max_mw"New value: +null
    • addedInput schema / properties / objective / description
      Added value: +"omitted: min_raw_power with export_minimums, else max_mw"
    • removedInput schema / properties / objective / type
      Removed value: -"string"
    • addedInput schema / properties / overclock_last
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "boolean"
      +    },
      +    {
      +      "const": "default",
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "build a row one machine short, the last one overclocked (1-2 Power Shards, checked against shards in hand plus those craftable from slugs); 'default' follows the shared setting",
      +  "title": "Overclock Last"
      +}
    • addedInput schema / properties / payback_hours
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "number"
      +    },
      +    {
      +      "const": "default",
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "hours of play extra, slower machines must repay in saved power: 0 builds plainly; stops 1, 2, 5, 10, 20, 50, 100; 'default' follows the shared setting. Stored per plan",
      +  "title": "Payback Hours"
      +}
    • addedInput schema / properties / power_price
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "number"
      +    },
      +    {
      +      "const": "default",
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "points per MWh the horizon prices power at; omit for the save's grid mix, 'default' puts a stored plan back on it",
      +  "title": "Power Price"
      +}
    • addedInput schema / properties / row_overclock
      Added value: +{
      +  "anyOf": [
      +    {
      +      "additionalProperties": {
      +        "enum": [
      +          "last",
      +          "spread",
      +          "default"
      +        ],
      +        "type": "string"
      +      },
      +      "type": "object"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "per recipe (exact name or class id): 'last' overclocks that row's last machine, 'spread' builds one more underclocked machine instead, 'default' follows overclock_last again. Overrides overclock_last for that row; rows not named keep their stored choice",
      +  "title": "Row Overclock"
      +}
  3. Changed6 schema fields changed
    • addedInput schema / properties / as_of
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "pin to one world state: a sav:… token from an earlier answer",
      +  "title": "As Of"
      +}
    • addedInput schema / properties / base_rev
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "integer"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "the plan version you read; needed to save over an existing plan",
      +  "title": "Base Rev"
      +}
    • addedInput schema / properties / required
      Added value: +{
      +  "anyOf": [
      +    {
      +      "items": {
      +        "type": "string"
      +      },
      +      "type": "array"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "recipes that must make their item; others for it are excluded",
      +  "title": "Required"
      +}
    • addedInput schema / properties / site_at
      Added value: +{
      +  "anyOf": [
      +    {
      +      "type": "string"
      +    },
      +    {
      +      "type": "null"
      +    }
      +  ],
      +  "default": null,
      +  "description": "with save_as: record where this plan will STAND -- 'x,y[,z]' in metres, 'me', a factory name, 'slab:<n>' or a run id (the footprint's centre)",
      +  "title": "Site At"
      +}
    • addedInput schema / properties / site_footprint
      Added value: +{
      +  "default": "",
      +  "description": "site footprint 'WxD' in metres; blank = the layout's own square",
      +  "title": "Site Footprint",
      +  "type": "string"
      +}
    • addedInput schema / properties / site_yaw_deg
      Added value: +{
      +  "default": 0,
      +  "description": "site orientation: degrees about world Z, positive +X towards +Y",
      +  "title": "Site Yaw Deg",
      +  "type": "number"
      +}
  4. First observedv0.1.0

TDQS

A3.6/5.0
Behavior4/5

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

Beyond the annotations, it discloses significant behavior: save_as stores the request rather than the solution, base_rev is required to overwrite, the default objective depends on export_minimums, exports replace defaults with special [] and 'MW' semantics, locked required recipes are refused, and the temporary solve token is explained. It does not cover every execution or error detail, but it is substantially richer than the annotations alone.

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

Conciseness4/5

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

The purpose is front-loaded and the dense notes are mostly justified for a 35-parameter tool. The telegraphic shorthand and occasional run-on punctuation reduce readability, but there is little wasted text.

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

Completeness4/5

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

For a complex LP planning tool with no output schema, it explains the key non-obvious defaults, save/overwrite behavior, export rules, and token handoff. It still omits details for several parameters and gives only broad output categories, so it is not fully complete but covers the main failure points.

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

Parameters4/5

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

With 74% schema description coverage, the description still adds meaningful semantics for high-impact parameters such as sources selector syntax, objective values and defaults, exports replacement behavior, required recipes, save_as/base_rev, and plan recall. Many of the 35 parameters are still left to the schema, so it is strong but not exhaustive.

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

Purpose4/5

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

The opening sentence states a specific verb and resource, 'Solve a factory plan by LP', and lists the planning outputs: machines, rates, power, exports, byproducts. It does not explicitly distinguish itself from nearby plan tools such as plan_from_factory or plan_layout, so it falls short of a 5.

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

Usage Guidelines2/5

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

The description is largely a parameter manual and never says when to choose plan_factory over plan_from_factory, plan_layout, site_plan, or edit_plan. Mentioning that the answer token is for 'other plan tools' is not enough to guide tool selection.

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