Skip to content

[BUG] openai-compat provider fails when using IP:port base URL #1057

Description

@yaoyi098

Bug Description

What happened

When using openai-compat LLM provider with a custom base URL containing a ip & port (e.g., http://10.43.46.12:3000/v1), the Higress AI provider's openaiCustomUrl field is set to the full URL including the port. Higress Console extracts the host:port from this URL and displays it as "自定义 OpenAI 服务主机域" (Custom OpenAI Service Host Domain) = 10.43.46.12:3000.

This causes Higress to use 10.43.46.12:3000 as the host domain for DNS resolution / upstream routing. Since 10.43.46.12:3000 is not a valid DNS hostname, resolution fails and the LLM endpoint is unreachable.

The port is already provided separately via openaiCustomServicePort (displayed as "选择服务" = openai-compat.dns:3000), so including it in openaiCustomUrl is redundant and breaks the host domain.

Actual Higress provider config after initialization:

Field Value
选择服务 openai-compat.dns:3000
自定义 OpenAI 服务路径 /v1
自定义 OpenAI 服务主机域 10.43.46.12:3000 ❌ (port included)

What I expected

The openaiCustomUrl should not include the port. The port should only come from openaiCustomServicePort. The "自定义 OpenAI 服务主机域" should be 10.43.46.12 (without port), and LLM requests should be forwarded to 10.43.46.12:3000 successfully.

Expected Higress provider config:

Field Value
选择服务 openai-compat.dns:3000
自定义 OpenAI 服务路径 /v1
自定义 OpenAI 服务主机域 10.43.46.12 ✅ (no port)

Steps to Reproduce

  1. Initialize the system: docker version. use one click script

  2. use local ai provider with port such as xx.xx.xxx.xx:3000/v1

AI Analysis

Root Cause

openaiCustomUrl is set to the full base URL (including port) instead of the URL with the port stripped. The port is duplicated — once in openaiCustomUrl (causing the host domain to include the port) and once in openaiCustomServicePort.

Affected code path 1: Go controller

File: hiclaw-controller/internal/initializer/initializer.go (~line 362)

raw := map[string]interface{}{
    "hiclawMode":              true,
    "openaiCustomUrl":         cfg.OpenAIBaseURL,           // ← "http://10.43.46.12:3000/v1" (port included)
    "openaiCustomServiceName": "openai-compat.dns",
    "openaiCustomServicePort": port,                         // ← 3000 (port already provided here)
}

Affected code path 2: Shell script

File: manager/scripts/init/setup-higress.sh (~line 221)

PROVIDER_BODY='{..."rawConfigs":{"openaiCustomUrl":"'"${OPENAI_BASE_URL}"'","openaiCustomServiceName":"openai-compat.dns","openaiCustomServicePort":'"${OC_PORT}"',"hiclawMode":true}}'
#                                              ↑ full URL with port            ↑ port already provided here

How it breaks

  1. Code sets openaiCustomUrl = http://10.43.46.12:3000/v1 (full URL with port)
  2. Higress Console extracts host:port from openaiCustomUrl → displays "自定义 OpenAI 服务主机域" = 10.43.46.12:3000
  3. Higress uses 10.43.46.12:3000 as the host domain for DNS resolution / upstream routing
  4. 10.43.46.12:3000 is not a valid DNS hostname → resolution fails → LLM endpoint unreachable

Suggested Fix

Strip the port from openaiCustomUrl. The port should only come from openaiCustomServicePort.

initializer.go:

u, _ := url.Parse(cfg.OpenAIBaseURL)
customUrl := fmt.Sprintf("%s://%s%s", proto, host, u.Path)   // "http://10.43.46.12/v1" (no port)

raw := map[string]interface{}{
    "hiclawMode":              true,
    "openaiCustomUrl":         customUrl,                    // "http://10.43.46.12/v1"
    "openaiCustomServiceName": "openai-compat.dns",
    "openaiCustomServicePort": port,                          // 3000
}

setup-higress.sh:

# Extract path from URL
OC_PATH="/${OC_URL_STRIP#*/}"
[ "${OC_PATH}" = "/" ] && OC_PATH=""

# Build openaiCustomUrl without port
OC_CUSTOM_URL="${OC_PROTO}://${OC_DOMAIN}${OC_PATH}"          # "http://10.43.46.12/v1" (no port)

PROVIDER_BODY='{..."rawConfigs":{"openaiCustomUrl":"'"${OC_CUSTOM_URL}"'","openaiCustomServiceName":"openai-compat.dns","openaiCustomServicePort":'"${OC_PORT}"',"hiclawMode":true}}'

Related Secondary Bug

ensureServiceSource() and EnsureAIProvider() in higress.go only use POST (treat 409 Conflict as success without updating the existing resource). This means even after fixing the code, existing incorrectly configured providers cannot be corrected by re-running the initializer — they must be manually deleted first. The shell script setup-higress.sh handles this correctly with GET → PUT if exists / POST if not, but the Go controller does not.

Relevant Logs

Component

Install / Setup

Version / Commit

v1.1.2

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions