feat: integrate higress-ai-gateway plugin into higress-clawdbot-integration skill (#3437)

This commit is contained in:
澄潭
2026-02-01 21:57:45 +08:00
committed by GitHub
parent 893b5feeb1
commit 04c35d7f6d
5 changed files with 593 additions and 0 deletions

View File

@@ -407,3 +407,188 @@ Configuration has been hot-reloaded (no restart needed).
- Verify the API key is correct
- Check provider documentation for key format
- Some providers require additional configuration (e.g., Azure, Bedrock)
## Clawdbot/OpenClaw Plugin Integration
The Higress AI Gateway plugin enables Clawdbot and OpenClaw to use Higress as a model provider with full support for auto-routing and model management.
### Installation
The plugin is automatically available as part of this skill. To install it into your Clawdbot/OpenClaw environment:
```bash
# Detect runtime and set variables
if command -v clawdbot &> /dev/null; then
RUNTIME="clawdbot"
RUNTIME_DIR="$HOME/.clawdbot"
elif command -v openclaw &> /dev/null; then
RUNTIME="openclaw"
RUNTIME_DIR="$HOME/.openclaw"
else
echo "Error: Neither clawdbot nor openclaw is installed"
exit 1
fi
# Install the plugin
PLUGIN_SRC_DIR="scripts/plugin"
PLUGIN_DEST_DIR="$RUNTIME_DIR/extensions/higress-ai-gateway"
if [ ! -d "$PLUGIN_SRC_DIR" ]; then
echo "Error: Plugin source not found at $PLUGIN_SRC_DIR"
exit 1
fi
echo "Installing Higress AI Gateway plugin for $RUNTIME..."
mkdir -p "$(dirname "$PLUGIN_DEST_DIR")"
if [ -d "$PLUGIN_DEST_DIR" ]; then
echo "Plugin already exists, updating..."
rm -rf "$PLUGIN_DEST_DIR"
fi
cp -r "$PLUGIN_SRC_DIR" "$PLUGIN_DEST_DIR"
echo "✓ Higress AI Gateway plugin installed at: $PLUGIN_DEST_DIR"
echo
echo "To configure the provider, run:"
echo " $RUNTIME models auth login --provider higress"
```
### Configuration
After installation, configure Higress as a model provider:
```bash
# For Clawdbot
clawdbot models auth login --provider higress
# For OpenClaw
openclaw models auth login --provider higress
```
The plugin will guide you through an interactive setup:
1. **Gateway URL**: HTTP endpoint for Higress AI Gateway (default: `http://localhost:8080`)
2. **Console URL**: Higress Console endpoint for routing config (default: `http://localhost:8001`)
3. **API Key**: Optional API key for authentication (leave empty for local deployments)
4. **Model List**: Comma-separated model IDs (plugin auto-detects available models)
5. **Auto-routing**: If you include `higress/auto` in the model list, configure the default fallback model
### Plugin Features
#### 1. Auto-routing Support
The plugin provides first-class support for Higress auto-routing:
- Use `higress/auto` as the model ID to enable intelligent routing
- Configure default fallback model during setup
- Auto-routing rules are managed separately via the `higress-auto-router` skill
#### 2. Dynamic Model Discovery
During configuration, the plugin:
- Tests connectivity to the gateway
- Fetches available models from the Console API
- Pre-populates the model list with discovered models
- Allows customization of the model list
#### 3. Smart URL Normalization
The plugin automatically:
- Strips trailing slashes from URLs
- Appends `/v1` suffix if missing
- Validates URL format before saving
#### 4. Profile Management
Creates appropriate credential profiles:
- `higress:local` - for local deployments without API key
- `higress:default` - for remote deployments with API key
### Plugin Structure
```
scripts/plugin/
├── index.ts # Plugin implementation (TypeScript)
├── package.json # NPM package metadata
└── openclaw.plugin.json # OpenClaw plugin manifest
```
**index.ts**: Main plugin code implementing the provider registration and authentication flow.
**package.json**: Declares the plugin as an OpenClaw extension with proper metadata.
**openclaw.plugin.json**: Plugin manifest describing supported providers and configuration schema.
### Integration with Skills
The plugin works seamlessly with related skills:
#### higress-auto-router
After plugin setup, use this skill to configure routing rules:
```bash
./get-ai-gateway.sh route add --model claude-opus-4.5 --trigger "深入思考"
```
See: [higress-auto-router](../higress-auto-router/SKILL.md)
#### agent-session-monitor
Track token usage and costs across sessions using gateway access logs:
```bash
python3 agent-session-monitor/scripts/webserver.py --log-path ./higress/logs/access.log
```
See: [agent-session-monitor](../agent-session-monitor/SKILL.md)
### Example: Full Setup Flow
```bash
# 1. Deploy Higress AI Gateway (via get-ai-gateway.sh)
./get-ai-gateway.sh start --non-interactive \
--dashscope-key sk-xxx \
--auto-routing
# 2. Detect and install plugin
if command -v clawdbot &> /dev/null; then
RUNTIME="clawdbot"
RUNTIME_DIR="$HOME/.clawdbot"
else
RUNTIME="openclaw"
RUNTIME_DIR="$HOME/.openclaw"
fi
mkdir -p "$RUNTIME_DIR/extensions"
cp -r scripts/plugin "$RUNTIME_DIR/extensions/higress-ai-gateway"
# 3. Configure provider
$RUNTIME models auth login --provider higress
# Follow interactive prompts to configure gateway URL, models, etc.
# 4. Test the integration
$RUNTIME chat --model higress/auto "Hello, test auto-routing!"
# 5. Configure routing rules (optional)
./get-ai-gateway.sh route add --model claude-opus-4.5 --trigger "深入思考"
```
### Troubleshooting
#### Plugin not recognized
- Verify plugin is installed at `~/.clawdbot/extensions/higress-ai-gateway` or `~/.openclaw/extensions/higress-ai-gateway`
- Check `package.json` contains correct `openclaw.extensions` field
- Restart Clawdbot/OpenClaw after installation
#### Gateway connection fails
- Ensure Higress AI Gateway container is running: `docker ps`
- Verify gateway URL is accessible: `curl http://localhost:8080/v1/models`
- Check firewall/network settings if using remote gateway
#### Models not available
- Run `clawdbot models list` or `openclaw models list` to verify provider is configured
- Check gateway logs: `docker logs higress-ai-gateway`
- Verify API keys are correctly configured in gateway
#### Auto-routing not working
- Confirm `higress/auto` is in your model list
- Check routing rules exist: `./get-ai-gateway.sh route list`
- Verify default model is configured
- Check gateway logs for routing decisions

View File

@@ -0,0 +1,92 @@
# Higress AI Gateway Plugin
OpenClaw/Clawdbot model provider plugin for Higress AI Gateway with auto-routing support.
## What is this?
This is a TypeScript-based provider plugin that enables Clawdbot and OpenClaw to use Higress AI Gateway as a model provider. It provides:
- **Auto-routing support**: Use `higress/auto` to intelligently route requests based on message content
- **Dynamic model discovery**: Auto-detect available models from Higress Console
- **Smart URL handling**: Automatic URL normalization and validation
- **Flexible authentication**: Support for both local and remote gateway deployments
## Files
- **index.ts**: Main plugin implementation
- **package.json**: NPM package metadata and OpenClaw extension declaration
- **openclaw.plugin.json**: Plugin manifest for OpenClaw
## Installation
This plugin is automatically installed when you use the `higress-clawdbot-integration` skill. See the parent SKILL.md for complete installation instructions.
### Manual Installation
If you need to install manually:
```bash
# Detect runtime
if command -v clawdbot &> /dev/null; then
RUNTIME_DIR="$HOME/.clawdbot"
elif command -v openclaw &> /dev/null; then
RUNTIME_DIR="$HOME/.openclaw"
else
echo "Error: Neither clawdbot nor openclaw is installed"
exit 1
fi
# Copy plugin files
mkdir -p "$RUNTIME_DIR/extensions/higress-ai-gateway"
cp -r ./* "$RUNTIME_DIR/extensions/higress-ai-gateway/"
# Configure provider
clawdbot models auth login --provider higress
# or
openclaw models auth login --provider higress
```
## Usage
After installation, configure Higress as a model provider:
```bash
clawdbot models auth login --provider higress
```
The plugin will prompt for:
1. Gateway URL (default: http://localhost:8080)
2. Console URL (default: http://localhost:8001)
3. API Key (optional for local deployments)
4. Model list (auto-detected or manually specified)
5. Auto-routing default model (if using higress/auto)
## Auto-routing
To use auto-routing, include `higress/auto` in your model list during configuration. Then use it in your conversations:
```bash
# Use auto-routing
clawdbot chat --model higress/auto "深入思考 这个问题应该怎么解决?"
# The gateway will automatically route to the appropriate model based on:
# - Message content triggers (configured via higress-auto-router skill)
# - Fallback to default model if no rule matches
```
## Related Resources
- **Parent Skill**: [higress-clawdbot-integration](../SKILL.md)
- **Auto-routing Configuration**: [higress-auto-router](../../higress-auto-router/SKILL.md)
- **Session Monitoring**: [agent-session-monitor](../../agent-session-monitor/SKILL.md)
- **Higress AI Gateway**: https://github.com/higress-group/higress-standalone
## Compatibility
- **OpenClaw**: v2.0.0+
- **Clawdbot**: v2.0.0+
- **Higress AI Gateway**: All versions
## License
Apache-2.0

View File

@@ -0,0 +1,284 @@
import { emptyPluginConfigSchema } from "openclaw/plugin-sdk";
const DEFAULT_GATEWAY_URL = "http://localhost:8080";
const DEFAULT_CONSOLE_URL = "http://localhost:8001";
const DEFAULT_CONTEXT_WINDOW = 128_000;
const DEFAULT_MAX_TOKENS = 8192;
// Common models that Higress AI Gateway typically supports
const DEFAULT_MODEL_IDS = [
// Auto-routing special model
"higress/auto",
// OpenAI models
"gpt-5.2",
"gpt-5-mini",
"gpt-5-nano",
// Anthropic models
"claude-opus-4.5",
"claude-sonnet-4.5",
"claude-haiku-4.5",
// Qwen models
"qwen3-turbo",
"qwen3-plus",
"qwen3-max",
"qwen3-coder-480b-a35b-instruct",
// DeepSeek models
"deepseek-chat",
"deepseek-reasoner",
// Other common models
"kimi-k2.5",
"glm-4.7",
"MiniMax-M2.1",
] as const;
function normalizeBaseUrl(value: string): string {
const trimmed = value.trim();
if (!trimmed) return DEFAULT_GATEWAY_URL;
let normalized = trimmed;
while (normalized.endsWith("/")) normalized = normalized.slice(0, -1);
if (!normalized.endsWith("/v1")) normalized = `${normalized}/v1`;
return normalized;
}
function validateUrl(value: string): string | undefined {
const normalized = normalizeBaseUrl(value);
try {
new URL(normalized);
} catch {
return "Enter a valid URL";
}
return undefined;
}
function parseModelIds(input: string): string[] {
const parsed = input
.split(/[\n,]/)
.map((model) => model.trim())
.filter(Boolean);
return Array.from(new Set(parsed));
}
function buildModelDefinition(modelId: string) {
const isAutoModel = modelId === "higress/auto";
return {
id: modelId,
name: isAutoModel ? "Higress Auto Router" : modelId,
api: "openai-completions",
reasoning: false,
input: ["text", "image"],
cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 },
contextWindow: DEFAULT_CONTEXT_WINDOW,
maxTokens: DEFAULT_MAX_TOKENS,
};
}
async function testGatewayConnection(gatewayUrl: string): Promise<boolean> {
try {
const response = await fetch(`${gatewayUrl}/v1/models`, {
method: "GET",
headers: { "Content-Type": "application/json" },
signal: AbortSignal.timeout(5000),
});
return response.ok || response.status === 401; // 401 means gateway is up but needs auth
} catch {
return false;
}
}
async function fetchAvailableModels(consoleUrl: string): Promise<string[]> {
try {
// Try to get models from Higress Console API
const response = await fetch(`${consoleUrl}/v1/ai/routes`, {
method: "GET",
headers: { "Content-Type": "application/json" },
signal: AbortSignal.timeout(5000),
});
if (response.ok) {
const data = (await response.json()) as { data?: { model?: string }[] };
if (data.data && Array.isArray(data.data)) {
return data.data
.map((route: { model?: string }) => route.model)
.filter((m): m is string => typeof m === "string");
}
}
} catch {
// Ignore errors, use defaults
}
return [];
}
const higressPlugin = {
id: "higress-ai-gateway",
name: "Higress AI Gateway",
description: "Model provider plugin for Higress AI Gateway with auto-routing support",
configSchema: emptyPluginConfigSchema(),
register(api) {
api.registerProvider({
id: "higress",
label: "Higress AI Gateway",
docsPath: "/providers/models",
aliases: ["higress-gateway", "higress-ai"],
auth: [
{
id: "api-key",
label: "API Key",
hint: "Configure Higress AI Gateway endpoint with optional API key",
kind: "custom",
run: async (ctx) => {
// Step 1: Get Gateway URL
const gatewayUrlInput = await ctx.prompter.text({
message: "Higress AI Gateway URL",
initialValue: DEFAULT_GATEWAY_URL,
validate: validateUrl,
});
const gatewayUrl = normalizeBaseUrl(gatewayUrlInput);
// Step 2: Get Console URL (for auto-router configuration)
const consoleUrlInput = await ctx.prompter.text({
message: "Higress Console URL (for auto-router config)",
initialValue: DEFAULT_CONSOLE_URL,
validate: validateUrl,
});
const consoleUrl = normalizeBaseUrl(consoleUrlInput);
// Step 3: Test connection (create a new spinner)
const spin = ctx.prompter.progress("Testing gateway connection…");
const isConnected = await testGatewayConnection(gatewayUrl);
if (!isConnected) {
spin.stop("Gateway connection failed");
await ctx.prompter.note(
[
"Could not connect to Higress AI Gateway.",
"Make sure the gateway is running and the URL is correct.",
"",
`Tried: ${gatewayUrl}/v1/models`,
].join("\n"),
"Connection Warning",
);
} else {
spin.stop("Gateway connected");
}
// Step 4: Get API Key (optional for local gateway)
const apiKeyInput = await ctx.prompter.text({
message: "API Key (leave empty if not required)",
initialValue: "",
}) || '';
const apiKey = apiKeyInput.trim() || "higress-local";
// Step 5: Fetch available models (create a new spinner)
const spin2 = ctx.prompter.progress("Fetching available models…");
const fetchedModels = await fetchAvailableModels(consoleUrl);
const defaultModels = fetchedModels.length > 0
? ["higress/auto", ...fetchedModels]
: DEFAULT_MODEL_IDS;
spin2.stop();
// Step 6: Let user customize model list
const modelInput = await ctx.prompter.text({
message: "Model IDs (comma-separated, higress/auto enables auto-routing)",
initialValue: defaultModels.slice(0, 10).join(", "),
validate: (value) =>
parseModelIds(value).length > 0 ? undefined : "Enter at least one model id",
});
const modelIds = parseModelIds(modelInput);
const hasAutoModel = modelIds.includes("higress/auto");
// FIX: Avoid double prefix - if modelId already starts with provider, don't add prefix again
const defaultModelId = hasAutoModel
? "higress/auto"
: (modelIds[0] ?? "qwen-turbo");
const defaultModelRef = defaultModelId.startsWith("higress/")
? defaultModelId
: `higress/${defaultModelId}`;
// Step 7: Configure default model for auto-routing
let autoRoutingDefaultModel = "qwen-turbo";
if (hasAutoModel) {
const autoRoutingModelInput = await ctx.prompter.text({
message: "Default model for auto-routing (when no rule matches)",
initialValue: "qwen-turbo",
});
autoRoutingDefaultModel = autoRoutingModelInput.trim(); // FIX: Add trim() here
}
return {
profiles: [
{
profileId: `higress:${apiKey === "higress-local" ? "local" : "default"}`,
credential: {
type: "token",
provider: "higress",
token: apiKey,
},
},
],
configPatch: {
models: {
providers: {
higress: {
baseUrl: `${gatewayUrl}/v1`,
apiKey: apiKey,
api: "openai-completions",
authHeader: apiKey !== "higress-local",
models: modelIds.map((modelId) => buildModelDefinition(modelId)),
},
},
},
agents: {
defaults: {
models: Object.fromEntries(
modelIds.map((modelId) => {
// FIX: Avoid double prefix - only add provider prefix if not already present
const modelRef = modelId.startsWith("higress/")
? modelId
: `higress/${modelId}`;
return [modelRef, {}];
}),
),
},
},
plugins: {
entries: {
"higress-ai-gateway": {
enabled: true,
config: {
gatewayUrl,
consoleUrl,
autoRoutingDefaultModel,
},
},
},
},
},
defaultModel: defaultModelRef,
notes: [
"Higress AI Gateway is now configured as a model provider.",
hasAutoModel
? `Auto-routing enabled: use model "higress/auto" to route based on message content.`
: "Add 'higress/auto' to models to enable auto-routing.",
`Gateway endpoint: ${gatewayUrl}/v1/chat/completions`,
`Console: ${consoleUrl}`,
"",
"🎯 Recommended Skills (install via Clawdbot conversation):",
"",
"1. Auto-Routing Skill:",
" Configure automatic model routing based on message content",
" https://github.com/alibaba/higress/tree/main/.claude/skills/higress-auto-router",
' Say: "Install higress-auto-router skill"',
"",
"2. Agent Session Monitor Skill:",
" Track token usage and monitor conversation history",
" https://github.com/alibaba/higress/tree/main/.claude/skills/agent-session-monitor",
' Say: "Install agent-session-monitor skill"',
],
};
},
},
],
});
},
};
export default higressPlugin;

View File

@@ -0,0 +1,10 @@
{
"id": "higress-ai-gateway",
"name": "Higress AI Gateway",
"description": "Model provider plugin for Higress AI Gateway with auto-routing support",
"providers": ["higress"],
"configSchema": {
"type": "object",
"additionalProperties": true
}
}

View File

@@ -0,0 +1,22 @@
{
"name": "@higress/higress-ai-gateway",
"version": "1.0.0",
"description": "Higress AI Gateway model provider plugin for OpenClaw with auto-routing support",
"main": "index.ts",
"openclaw": {
"extensions": ["./index.ts"]
},
"keywords": [
"openclaw",
"higress",
"ai-gateway",
"model-router",
"auto-routing"
],
"author": "Higress Team",
"license": "Apache-2.0",
"repository": {
"type": "git",
"url": "https://github.com/alibaba/higress"
}
}