How to Configure Custom Model Endpoints for OpenDeepWiki: A Complete Guide
You can configure custom model endpoints for OpenDeepWiki by setting the global ENDPOINT environment variable for default behavior or creating per-model configurations via the Admin API at /admin/tools/models, where the ModelConfig entity stores custom URLs that override global settings during chat requests.
OpenDeepWiki is an AI-driven wiki generation platform that routes LLM requests through a flexible endpoint configuration system. Understanding how to configure custom model endpoints for OpenDeepWiki enables you to integrate private inference servers, corporate proxies, or multiple cloud providers within a single deployment. The architecture implements a hierarchical resolution strategy where per-model settings in the ModelConfig entity take precedence over global fallback values defined in AiRequestOptions.
Global Endpoint Configuration via Environment Variables
The system defines baseline connectivity parameters through the AiRequestOptions class bound during application startup. In src/OpenDeepWiki/Program.cs, the configuration pipeline registers these options and implements a fallback mechanism that checks the ENDPOINT environment variable when no explicit value exists in appsettings.json.
The registration logic appears at lines 31-40:
builder.Services.AddOptions<AiRequestOptions>()
.Bind(builder.Configuration.GetSection("AI"))
.PostConfigure(options => {
if (string.IsNullOrWhiteSpace(options.Endpoint)) {
// Fallback to ENV var ENDPOINT if not set in appsettings
options.Endpoint = builder.Configuration["ENDPOINT"];
}
});
When a model configuration lacks a specific endpoint, the chat service automatically resolves to this global value. This approach suits homogeneous environments where all models route through a single gateway or API proxy.
Per-Model Endpoint Configuration via Admin API
For heterogeneous deployments requiring different endpoints per provider, OpenDeepWiki stores custom configurations in the ModelConfig entity defined in src/OpenDeepWiki.Entities/Tools/ModelConfig.cs. This entity includes nullable fields for Endpoint and ApiKey, allowing granular overrides at the individual model level.
The entity structure at lines 34-42 specifies:
public class ModelConfig : AggregateRoot<string>
{
public string? Endpoint { get; set; } // Custom API endpoint
public string? ApiKey { get; set; } // Optional per-model key
// Additional properties omitted for brevity
}
Creating a Custom Model Configuration
Administrators manage these records through the REST API exposed in src/OpenDeepWiki/Endpoints/Admin/AdminToolsEndpoints.cs. The POST /admin/tools/models endpoint accepts a ModelConfigRequest payload and persists the configuration via AdminToolsService.CreateModelConfigAsync.
The endpoint registration at lines 78-84 handles incoming requests:
modelGroup.MapPost("/", async (
[FromBody] ModelConfigRequest request,
[FromServices] IAdminToolsService toolsService) =>
{
var result = await toolsService.CreateModelConfigAsync(request);
return Results.Ok(new { success = true, data = result });
});
The service implementation in src/OpenDeepWiki/Services/Admin/AdminToolsService.cs (lines 301-310) maps the request to the entity:
public async Task<ModelConfigDto> CreateModelConfigAsync(ModelConfigRequest request)
{
var config = new ModelConfig {
Id = Guid.NewGuid().ToString(),
Name = request.Name,
Provider = request.Provider,
ModelId = request.ModelId,
Endpoint = request.Endpoint, // Custom endpoint stored here
ApiKey = request.ApiKey,
// ...
};
_context.ModelConfigs.Add(config);
await _context.SaveChangesAsync();
// ...
}
How the Chat Service Resolves Endpoints
During request processing, ChatAssistantService located in src/OpenDeepWiki/Services/Chat/ChatAssistantService.cs retrieves the appropriate configuration and constructs AiRequestOptions. The resolution logic at lines 432-435 demonstrates the priority system:
var modelConfig = await GetModelConfigAsync(request.ModelId, config, cancellationToken);
var requestOptions = new AiRequestOptions {
ApiKey = modelConfig.ApiKey, // Falls back to global if null
Endpoint = modelConfig.Endpoint, // Falls back to global if null
RequestType = ParseRequestType(modelConfig.Provider)
};
If modelConfig.Endpoint contains a non-null value, the system routes the request to that specific URL rather than the global default.
Configuration Verification Checklist
Before deploying custom endpoints to production, verify the following:
- Global fallback: Confirm the
ENDPOINTenvironment variable orappsettings.jsonsectionAI:Endpointcontains a valid URL if relying on default behavior - Database record: Query the
ModelConfigstable to ensure theEndpointfield is populated for the specific model ID - API response: Verify that
POST /admin/tools/modelsreturns HTTP 200 with a success flag and the generatedId - Request payload: Ensure chat requests include the correct
ModelIdcorresponding to your custom configuration - Runtime logs: Inspect logs for entries showing the resolved endpoint URL during chat stream initialization
Practical Configuration Examples
Setting a Global Fallback Endpoint
Configure the environment variable before launching the application:
export ENDPOINT="https://api.openai.com/v1/chat/completions"
export CHAT_API_KEY="sk-XXXXXXXXXXXXXXXX"
dotnet run --project src/OpenDeepWiki/OpenDeepWiki.csproj
Alternatively, add the configuration to appsettings.Development.json:
{
"AI": {
"Endpoint": "https://api.openai.com/v1/chat/completions",
"ApiKey": "sk-XXXXXXXXXXXXXXXX"
}
}
Creating a Model with Custom Endpoint via API
Use the administrative endpoint to register a model routing through a private proxy:
curl -X POST http://localhost:5000/admin/tools/models \
-H "Content-Type: application/json" \
-d '{
"Name": "MyCustomClaude",
"Provider": "Anthropic",
"ModelId": "claude-3-5-sonnet-20240620",
"Endpoint": "https://my-proxy.example.com/v1/claude",
"ApiKey": "my-proxy-key",
"IsDefault": false,
"IsActive": true,
"Description": "Claude via internal proxy"
}'
The API returns the persisted configuration including the generated identifier:
{
"success": true,
"data": {
"Id": "c9e5a7b5-2f8d-4a1e-9f4c-7e2f6d3a1b9c",
"Name": "MyCustomClaude",
"Endpoint": "https://my-proxy.example.com/v1/claude",
"HasApiKey": true,
"IsActive": true
}
}
Sending Chat Requests to Custom Endpoints
Reference the custom model by its Id in chat requests:
POST http://localhost:5000/chat/assistant/stream
Content-Type: application/json
{
"ModelId": "c9e5a7b5-2f8d-4a1e-9f4c-7e2f6d3a1b9c",
"Messages": [
{ "Role": "user", "Content": "Summarize the repository structure." }
]
}
The service resolves the custom endpoint from the database and routes the request accordingly.
Summary
- Global configuration uses the
ENDPOINTenvironment variable orAIconfiguration section inappsettings.json, registered viaAddOptions<AiRequestOptions>()inProgram.cs - Per-model configuration overrides globals through the
ModelConfigentity stored in the database, manageable viaPOST /admin/tools/models - Resolution priority follows a hierarchy: per-model
Endpointproperty → globalAiRequestOptions.Endpoint→ null (error condition) - Administrative functions are implemented in
AdminToolsService.cswith CRUD operations forModelConfigrecords - Runtime resolution occurs in
ChatAssistantService.cs, which buildsAiRequestOptionsusing the resolved endpoint and API key
Frequently Asked Questions
Can I configure different endpoints for different models in OpenDeepWiki?
Yes. Create separate ModelConfig records via the Admin API at /admin/tools/models, each specifying a unique Endpoint URL. The ChatAssistantService resolves the appropriate endpoint based on the ModelId provided in the chat request, allowing you to route individual models to different providers or proxies within the same instance.
What happens if a model configuration has no endpoint specified?
When the Endpoint property of a ModelConfig entity is null or empty, the system falls back to the global AiRequestOptions.Endpoint value configured during startup. This fallback is established in Program.cs through the PostConfigure delegate, which checks the ENDPOINT environment variable if no explicit value exists in configuration files.
How do I update an existing model's endpoint?
Send a PUT request to /admin/tools/models/{id} with the updated Endpoint value in the JSON payload. The AdminToolsService.UpdateModelConfigAsync method handles the persistence, updating the ModelConfig entity in the database. Subsequent chat requests using that ModelId will immediately use the new endpoint without requiring application restart.
Is the API key also configurable per model or only globally?
Both. The ModelConfig entity includes an ApiKey property that, when populated, overrides the global API key for that specific model. If left null, the system uses the global key from AiRequestOptions. This dual-layer approach supports scenarios where different models require different authentication credentials or where some models use unauthenticated local endpoints while others use cloud APIs.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →