_ _ _ _
/\ \ /\ \ / /\ _\ \
\ \ \ / \ \____ / / \ /\__ \
/\ \_\ / /\ \_____\ / / /\ \__ / /_ \_\
/ /\_// / /\/___ // / /\ \___\ / / /\/_/
_ / / / / / / / / / \ \ \ \/___// / /
/\ \ / / / / / / / / / \ \ \ / / /
\ \_\/ / / / / / / / /_ \ \ \ / / / ____
/ / /_/ / / \ \__/ / //_\__/ / / / /_/_/ ___/\
/ / /__\/ / \ \___\/ / \ \/___/ / /_______/\__/
\/_______/ \/_____/ \_____\/ \_______\/
Declarative behavior-tree agents as clean Python combinators.
curl -fsSL https://cantorindustries.com/jdsl-py/install.sh | bash
Determinism lives in the tree. The tree structure is the call structure. No object-literal DSLs parsing strings in the dark.
The model enters only at predict leaves, guided cleanly by DSPy-style signatures like "message -> category".
A react leaf hands the model your native Python @tools and lets it pick, chain, and execute them until it answers.
Use the jdsl harness to capture frontier-model traces and compile proven paths into portable policies for smaller, frozen models.
from jdsl import root, seq, sel, act, check, predict # The tree structure is the call structure. skill = ( root("Triage") .model("deepseek-chat") .do(seq( predict("message -> category"), sel( seq(check("category", "billing"), act(route_to_billing)), seq(check("category", "support"), act(route_to_support)), act(route_to_human) ) )) )