Catalog search (bt.catalog)¶
Real products to choose from: the catalog's published index, filtered the way a requirement reads. See Selecting parts.
cands = bt.catalog.search("gripper.parallel", stroke_mm=150, payload_kg=2.3)
cands[0].identify(scene, "ur5e/tool")
bt.catalog.search_for(scene.requirements()["eye"], level="V2")
catalog
¶
Search the botrail catalog — real products to choose from.
The catalog (the Hugging Face dataset botrail/botrail-catalog) publishes an
index.json with every product's category, maker, numeric specs and
validation level. This module reads that index and filters it the way a
requirement reads — minimums on spec keys — so a person or an agent picks
from products that exist, with the numbers that decide the pick in view.
botrail still does not choose: :func:search returns candidates, and
:meth:Product.identify writes the one you picked onto the cell.
cands = bt.catalog.search("gripper.parallel", stroke_mm=150, payload_kg=2.3)
cands[0].identify(scene, "ur5e/tool") # set_part with the catalog id and its specs
bt.catalog.search_for(scene.requirements()["eye"]) # straight from a requirement row
Spec keys are the requirement vocabulary of :mod:botrail.select — the
catalog's specs / mechanical / electrical numbers, read through the
same aliases. A product that does not state a filtered key does not match
(unknown is not a pass). Results are ordered by validation level, then by
closeness to the requested minimums, then by id — the same query gives the
same list.
The index is fetched with huggingface_hub (pip install botrail[catalog])
and pinned to a dataset commit; a copy already in the Hugging Face cache is
used when the hub cannot be reached, and index(path=...) /
BOTRAIL_CATALOG_INDEX read a local file (a builder's dist/index.json).
ALIASES
module-attribute
¶
ALIASES = {
"payload_kg": ("payload_kg",),
"reach_mm": ("reach_mm",),
"stroke_mm": ("stroke_mm", "opening_mm"),
"aperture_mm": ("aperture_mm",),
"grip_force_n": (
"grip_force_max_n",
"grip_force_min_n",
),
"sensing_range_mm": (
"sensing_range_mm",
"range_mm",
"max_range_mm",
),
"fov_deg": ("fov_h_deg", "hfov_deg", "fov_deg"),
"resolution_h_px": ("resolution_h_px",),
"resolution_v_px": ("resolution_v_px",),
"max_range_mm": ("max_range_mm",),
"min_range_mm": ("min_range_mm",),
"scan_fov_deg": ("scan_fov_deg",),
"range_mm": (
"range_mm",
"max_range_mm",
"sensing_range_mm",
),
"protective_height_mm": (
"protective_height_mm",
"height_mm",
),
"length_mm": ("length_mm",),
"width_mm": ("width_mm", "belt_width_mm"),
"speed_mps": (
"max_speed_mps",
"speed_max_mps",
"speed_mps",
),
"max_speed_mps": (
"max_speed_mps",
"speed_max_mps",
"speed_mps",
),
"max_climb_mps": ("max_climb_mps",),
"max_descent_mps": ("max_descent_mps",),
"flight_time_min": ("flight_time_min",),
"load_kg": (
"load_kg",
"capacity_kg",
"max_load_kg",
"payload_kg",
),
"output_a": ("output_a", "current_a"),
"di": ("di",),
"do": ("do",),
"ai": ("ai",),
"ao": ("ao",),
"safe_di": ("safe_di",),
"safe_do": ("safe_do",),
}
dict() -> new empty dictionary dict(mapping) -> new dictionary initialized from a mapping object's (key, value) pairs dict(iterable) -> new dictionary initialized as if via: d = {} for k, v in iterable: d[k] = v dict(**kwargs) -> new dictionary initialized with the name=value pairs in the keyword argument list. For example: dict(one=1, two=2)
LEVELS
module-attribute
¶
Built-in immutable sequence.
If no argument is given, the constructor returns an empty tuple. If iterable is specified the tuple is initialized from iterable's items.
If the argument is a tuple, the return value is the same object.
REPO_ID
module-attribute
¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.str() (if defined) or repr(object). encoding defaults to sys.getdefaultencoding(). errors defaults to 'strict'.
REPO_URL
module-attribute
¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.str() (if defined) or repr(object). encoding defaults to sys.getdefaultencoding(). errors defaults to 'strict'.
Index
¶
The catalog index: every product, and the search over them.
get
¶
get(query: str) -> Product
A product by exact id, or by a unique id whose path segments
contain the query's segments in order (universal_robots/ur5e);
several revisions of one product resolve to the newest.
search
¶
search(
category: Optional[str] = None,
*,
kind: Optional[str] = None,
manufacturer: Optional[str] = None,
level: Optional[str] = None,
text: Optional[str] = None,
limit: Optional[int] = None,
**specs: Any,
) -> list[Product]
Products matching a category (prefix: gripper matches
gripper.parallel), a maker, a minimum validation level, a text
fragment of id or name, and spec filters: key=value means the
product states key >= value; key__max=value means <= value;
a string value must equal the product's string spec. Ordered by
validation level (best first), then closeness to the minimums
(smallest headroom first), then id.
Product
¶
One catalog entry as the index lists it.
distribution
class-attribute
¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.str() (if defined) or repr(object). encoding defaults to sys.getdefaultencoding(). errors defaults to 'strict'.
kind
class-attribute
¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.str() (if defined) or repr(object). encoding defaults to sys.getdefaultencoding(). errors defaults to 'strict'.
attributes
¶
Every numeric spec the product states, flattened — what lands on
the part when it is identified, and what :func:search filters on.
identify
¶
identify(
scene,
target: str,
*,
kind: Optional[str] = None,
qty: int = 1,
**overrides: Any,
) -> str
Write this product onto a resident: set_part(target, catalog=(id,
revision), manufacturer, model, category, attributes). The numeric
specs come along, so the requirement check reads them. overrides
add or replace attributes (mass_kg=...). Returns what set_part
returns (the kind the target resolved to).
value
¶
The number answering a requirement key, through the same aliases the requirement check uses.
index
¶
index(
*,
revision: Optional[str] = None,
path: Union[str, Path, None] = None,
offline: Optional[bool] = None,
refresh: bool = False,
) -> Index
The catalog index. path (or BOTRAIL_CATALOG_INDEX) reads a local
index.json; otherwise the hub resolves revision (default: the newest
commit) and downloads the index pinned to it. When the hub cannot be
reached the newest index already in the Hugging Face cache is used —
offline=True goes straight to the cache, offline=False never does.
Hub lookups are cached per process (refresh=True asks again).
search
¶
search(
category: Optional[str] = None,
*,
index: Union[Index, str, Path, None] = None,
revision: Optional[str] = None,
kind: Optional[str] = None,
manufacturer: Optional[str] = None,
level: Optional[str] = None,
text: Optional[str] = None,
limit: Optional[int] = None,
**specs: Any,
) -> list[Product]
Products in the catalog that match — see :meth:Index.search.
index takes an :class:Index or a path to one; otherwise the
published index is used (pinned to revision when given).
bt.catalog.search("gripper.parallel", stroke_mm=150, payload_kg=2.3)
bt.catalog.search("manipulator", reach_mm=900, payload_kg=6, level="V3")
bt.catalog.search(kind="spec", category="structure.fence")
search_for
¶
search_for(
row,
*,
category: Optional[str] = None,
index: Union[Index, str, Path, None] = None,
**extra: Any,
) -> list[Product]
Candidates for one requirement row (scene.requirements()["tool"]):
its category and every >= requirement become the filters; extra
adds or overrides filters (level="V3", ip_rating="IP54").