Gadget Ecosystem
llmist supports loading gadgets from npm packages and git repositories, enabling a rich ecosystem of reusable tools.
Dhalsim
Section titled “Dhalsim”Dhalsim is the official browser automation package for llmist, providing gadgets for web navigation, screenshots, and autonomous browsing.
Installation
Section titled “Installation”# Use directly (auto-installed)bunx @llmist/cli agent "Navigate to apple.com" -g dhalsim
# Specific version# Use directly (auto-installed)npx @llmist/cli agent "Navigate to apple.com" -g dhalsim
# Specific versionAvailable Presets
Section titled “Available Presets”| Preset | Description | Gadgets |
|---|---|---|
all | All browser automation gadgets | Full suite |
minimal | Basic navigation and capture | Navigate, Screenshot, GetFullPageContent |
readonly | Navigation and read-only operations | No form filling or clicking |
subagent | Autonomous browser agent | BrowseWeb |
# Use a presetbunx @llmist/cli agent "Research topic" -g dhalsim:subagent
# Combine presets with local gadgetsbunx @llmist/cli agent "Complex task" \ -g dhalsim:minimal \ -g ./my-gadget.ts# Use a presetnpx @llmist/cli agent "Research topic" -g dhalsim:subagent
# Combine presets with local gadgetsnpx @llmist/cli agent "Complex task" \ -g dhalsim:minimal \ -g ./my-gadget.tsIndividual Gadgets
Section titled “Individual Gadgets”When using dhalsim:all or dhalsim, you get:
| Gadget | Description |
|---|---|
Navigate | Navigate to a URL |
Screenshot | Capture a screenshot |
GetFullPageContent | Get full page text/HTML |
Click | Click an element |
Type | Type into an input |
ScrollPage | Scroll the page |
WaitForElement | Wait for element to appear |
BrowseWeb Subagent
Section titled “BrowseWeb Subagent”The dhalsim:subagent preset provides BrowseWeb, an autonomous browser agent:
bunx @llmist/cli agent "Find the pricing for Anthropic's API" -g dhalsim:subagentnpx @llmist/cli agent "Find the pricing for Anthropic's API" -g dhalsim:subagentBrowseWeb spawns a nested agent that:
- Opens a browser
- Plans a browsing strategy
- Navigates, clicks, and extracts information
- Returns findings to the parent agent
Example usage in code:
// The BrowseWeb gadget is a subagentclass BrowseWeb extends Gadget({ description: 'Browse the web autonomously to complete a task', schema: z.object({ task: z.string().describe('What to accomplish'), startUrl: z.string().url().optional(), }),}) { async execute(params, ctx) { // Spawns a nested agent with browser gadgets const result = await new AgentBuilder() .withParentContext(ctx!) .withModel('haiku') .withGadgets(Navigate, Screenshot, Click, Type) .askAndCollect(params.task); return result; }}Loading from Git
Section titled “Loading from Git”Load gadgets directly from git repositories:
# Public repositorybunx @llmist/cli agent "task" -g git+https://github.com/user/my-gadgets.git
# Specific branch/tagbunx @llmist/cli agent "task" -g git+https://github.com/user/my-gadgets.git#v1.0.0
# Private repository (uses git credentials)bunx @llmist/cli agent "task" -g git+https://github.com/org/private-gadgets.git# Public repositorynpx @llmist/cli agent "task" -g git+https://github.com/user/my-gadgets.git
# Specific branch/tagnpx @llmist/cli agent "task" -g git+https://github.com/user/my-gadgets.git#v1.0.0
# Private repository (uses git credentials)npx @llmist/cli agent "task" -g git+https://github.com/org/private-gadgets.gitRepository Structure
Section titled “Repository Structure”Git gadget repositories should export gadgets from their entry point:
my-gadgets/├── package.json├── index.ts # Exports gadgets└── src/ ├── floppy.ts └── arcade.tsexport { FloppyDisk } from './src/floppy.js';export { ArcadeHighScore } from './src/arcade.js';Creating Your Own Package
Section titled “Creating Your Own Package”Package Structure
Section titled “Package Structure”my-gadget-package/├── package.json├── index.ts├── src/│ ├── gadget-a.ts│ └── gadget-b.ts└── presets.ts # Optional: define presetspackage.json
Section titled “package.json”{ "name": "my-gadget-package", "version": "1.0.0", "type": "module", "main": "index.ts", "peerDependencies": { "llmist": "^8.0.0" }, "llmist": { "presets": { "all": ["GadgetA", "GadgetB"], "minimal": ["GadgetA"] } }}Exporting Gadgets
Section titled “Exporting Gadgets”import { Gadget, z } from 'llmist';
export class GadgetA extends Gadget({ description: 'Does something useful', schema: z.object({ input: z.string(), }),}) { async execute(params: this['params']): Promise<string> { return `Processed: ${params.input}`; }}
export class GadgetB extends Gadget({ description: 'Does something else', schema: z.object({ value: z.number(), }),}) { execute(params: this['params']): string { return `Result: ${params.value * 2}`; }}Defining Presets
Section titled “Defining Presets”Add presets to package.json:
{ "llmist": { "presets": { "all": ["GadgetA", "GadgetB", "GadgetC"], "core": ["GadgetA"], "advanced": ["GadgetB", "GadgetC"] } }}Users can then:
bunx @llmist/cli agent "task" -g my-package:corebunx @llmist/cli agent "task" -g my-package:advancednpx @llmist/cli agent "task" -g my-package:corenpx @llmist/cli agent "task" -g my-package:advancedPackage Manifest Types
Section titled “Package Manifest Types”Import manifest types from llmist for type-safe package development:
import type { LLMistPackageManifest, SubagentManifestEntry, PresetDefinition, SessionManifestEntry,} from 'llmist';import { parseManifest, hasPreset, listSubagents, getSubagent } from 'llmist';Full manifest structure:
const manifest: LLMistPackageManifest = { // Entry point for all gadgets gadgets: './dist/index.js',
// Factory function entry point (optional) factory: './dist/index.js',
// Presets: array of gadget names or "*" for all presets: { minimal: ['Navigate', 'Screenshot'], readonly: ['Navigate', 'GetFullPageContent', 'Screenshot'], all: '*', // All exported gadgets },
// Subagent definitions (optional) subagents: { BrowseWeb: { entryPoint: './dist/index.js', export: 'Dhalsim', // Export name description: 'Autonomous web browser agent', defaultModel: 'sonnet', maxIterations: 15, }, },
// Session factory metadata (optional) session: { factory: 'getSessionManager', type: 'browser', },};Parsing utilities:
import { readFileSync } from 'fs';import { parseManifest, hasPreset, getPresetGadgets, listSubagents } from 'llmist';
// Parse manifest from package.jsonconst pkg = JSON.parse(readFileSync('package.json', 'utf-8'));const manifest = parseManifest(pkg);
// Check presetsif (hasPreset(manifest, 'minimal')) { const gadgets = getPresetGadgets(manifest, 'minimal'); // ['Navigate', 'Screenshot']}
// List subagentsconst subagentNames = listSubagents(manifest);// ['BrowseWeb']Publishing to npm
Section titled “Publishing to npm”npm publishUsers install with:
bunx @llmist/cli agent "task" -g my-packagenpx @llmist/cli agent "task" -g my-packageSecurity Considerations
Section titled “Security Considerations”When using third-party gadgets:
- Review the source - Check the repository before using
- Pin versions - Use specific versions in production:
-g [email protected] - Use gadget approval - Enable approval for dangerous operations:
[agent]gadget-approval = { "*" = "approval-required" }
- Sandbox execution - Consider running in isolated environments
Combining Sources
Section titled “Combining Sources”Mix local, npm, git, and built-in gadgets:
bunx @llmist/cli agent "Complex research task" \ -g ./local-gadget.ts \ -g dhalsim:minimal \ -g builtin:ReadFile \ -g git+https://github.com/user/my-gadgets.gitnpx @llmist/cli agent "Complex research task" \ -g ./local-gadget.ts \ -g dhalsim:minimal \ -g builtin:ReadFile \ -g git+https://github.com/user/my-gadgets.gitSee Also
Section titled “See Also”- CLI Gadgets - Creating local gadgets
- CLI Configuration - Gadget approval settings
- Subagents - Building subagent gadgets