feat(plugin-ai): add aimlapi.com as an LLM provider - #1
Open
Lookoff-AIMLAPI wants to merge 3 commits into
Open
Conversation
Admins can already reach AI/ML API through `openai-completions` with a custom base URL, but that route leaves the service unnamed in the provider list, offers no model catalog, and sends no attribution. A first-class entry gives the provider its own name and description, loads the account's Chat Completions catalog, and lets AI/ML API attribute the traffic to NocoBase. The provider follows the shengsuanyun shape (LangChain `ChatOpenAI` over the OpenAI-compatible Chat Completions API, plus a `listModels` override) and the orcarouter shape for attribution headers. `HTTP-Referer` and `X-Title` identify NocoBase as the calling application and stay overridable per service; the `X-AIMLAPI-*` pair identifies the integration. All four are scoped to the AI/ML API origin, because `baseURL` is user-configurable and attribution must not ride a request to another vendor or to a proxy that merely fronts the same API. No model ids are hardcoded: the catalog is fetched at configuration time and narrowed to entries the Chat Completions client can actually drive, so the list cannot rot.
Puts aimlapi.com first in the provider selector's hand-written sort order and seeds the existing per-provider recommended-model list, which is empty for every other provider today, so the AI/ML API entry carries the "Recommended" tag. This is partnership placement, not a functional change, and it is deliberately isolated in one commit so it can be dropped before the provider itself is offered upstream. The four model ids were checked against the live catalog (ids and aliases) and are all `openai/chat-completions` entries.
The placeholder part_nocobase was a readable stand-in chosen before the partner was registered. Registration mints the id server-side, so the real value is part_vIQFIgEDs9Yk0yizVcgoM5Sp. A wrong or unknown partner id is accepted with a 200 and silently not attributed, so this would not have surfaced at runtime.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This is a ...
Motivation
Admins can already reach AI/ML API today through
openai-completionswith a custombaseURL, so this is not newcapability — it buys discoverability, a correct model list and attribution. Configured that way the service shows up
in the provider list as "OpenAI (completions)", the model picker is empty unless every id is typed by hand, and
nothing tells AI/ML API which application the traffic came from.
This adds
aimlapi.comas a first-class LLM provider inplugin-ai, following the shape of the two most recentprovider additions in this repo (
shengsuanyun,orcarouter).Description
Server —
src/server/llm-providers/aimlapi.tsAimlapiProvider extends LLMProvider, LangChainChatOpenAIover the OpenAI-compatible Chat Completions API.https://api.aimlapi.com/v1; user-overridable per service like every other provider.listModels()fetchesGET {baseURL}/modelswith the configured key and narrows the catalog to entries the ChatCompletions client can actually drive (
type === "openai/chat-completions"). The catalog mixes image, video,speech and embedding models into the same list, so an unfiltered list would offer models that cannot be chatted
with. Entries with no
typeare kept, so a user pointingbaseURLat another OpenAI-compatible endpoint stillgets a list.
orcarouter.tswhich already injectsHTTP-Referer/X-Titlefrom serviceoptions:
HTTP-Referer: https://github.com/nocobase/nocobaseandX-Title: NocoBase— these identify NocoBase as thecalling application, not AI/ML API, and both stay overridable per service through the settings form.
X-AIMLAPI-Partner-ID/X-AIMLAPI-Source— identify the integration itself.api.aimlapi.comorigin.baseURLis user-configurable, so a service could pointat another vendor or at a proxy that merely fronts the same API; neither should receive them.
mutate it.
Client (v2) — the provider settings form (API key + optional referer/title, mirroring OrcaRouter's), the provider
options registration, and a localized description.
openAICompletionFieldsis reused for model options rather thanduplicating an identical field list.
i18n — one new string, added to both
en-USandzh-CN.Risks are contained: nothing existing changes behaviour. The one shared file with more than an added line is
src/client-v2/llm-providers/index.ts, where the provider is appended to the two builtin registries.Fork-only commit
The second commit,
chore(aimlapi): fork-only placement — do not send upstream, is partnership placement rather thana functional change and is deliberately isolated so it can be dropped before this is offered upstream:
aimlapifirst ingetProviderSortIndex's hand-written sort order;recommendedModels.aimlapi, which is empty for every provider today, so the entry carries the existing"Recommended" tag.
Only the first commit is intended for upstream.
Verification
Test baseline recorded on a pristine checkout first, then re-run with the change:
yarn test packages/plugins/@nocobase/plugin-ai --runyarn test:client packages/plugins/@nocobase/plugin-ai/src/client-v2 --runThe 6 collection failures are identical before and after and unrelated to this change:
jwa→buffer-equal-constant-timethrowsTypeError: Cannot read properties of undefined (reading 'prototype')on Node26 (
SlowBufferremoval). Affected suites:ai-files-access,ai-workflow-tasks,checkpoint,knowledge-base-retrieval-strategy-migration,mcp-client-events,workflow-files.The 11 new tests cover the base URL, the display name, the header set, the origin scoping, the per-service override
path, and the catalog filter. One of them asserts the partner id matches
^part_[A-Za-z0-9]{1,64}$— a malformed idis dropped silently by the gateway, so a typo would otherwise be invisible at runtime.
yarn build— full monorepo build: exit 0. (yarn build @nocobase/plugin-aialone fails on a fresh checkout because the core packages have nobuilt declarations yet; the full build produces
packages/plugins/@nocobase/plugin-ai/dist/server/llm-providers/aimlapi.jsand
aimlapi.d.ts.)yarn eslinton every touched file: clean, exit 0.One real inference call through the provider, not a mock and not a raw curl — a temporary vitest file that
constructs
AimlapiProviderand calls it, with a real key passed via env (the file is not part of this diff):So: catalog listing (353 chat models out of 936 catalog entries), a chat completion, and a tool call all go through
the provider added here, with the four headers on the wire.
The four model ids in the fork-only
recommendedModelsseed were each checked against the live catalog by id andalias and are all
openai/chat-completionsentries:openai/gpt-4o,anthropic/claude-sonnet-4.5,google/gemini-2.5-pro,deepseek/deepseek-chat. Noteanthropic/claude-sonnet-4-5(hyphen) is neither an id noran alias; the dotted form is the real one.
Not verified
settings page. The client changes are covered only by the existing unit tests.
LLMProvider.stream) was not exercised live, only the non-streaminginvokepath.Changelog
aimlapi.comas an LLM provideraimlapi.com大模型服务商Docs
Checklists