Migrating to Typed AI Deployments
What Changed
Previously, AI model deployments were configured as string properties on AIProviderConnection — for example, ChatDeploymentName, UtilityDeploymentName, EmbeddingDeploymentName, and ImagesDeploymentName. This meant deployments were tightly coupled to their connection and had no independent identity.
In the new architecture, AIDeployment is a first-class typed entity with:
Type— The deployment purpose:Chat,Utility,Embedding,Image, orSpeechToTextIsDefault— Whether this deployment is the default for its type within its connection- Independent identity — Each deployment has its own record and can be referenced by ID
AI Profiles and Chat Interactions now reference deployments by ID (ChatDeploymentId, UtilityDeploymentId) rather than relying on a connection name to resolve deployment names.
Deployment Resolution Fallback
When resolving a deployment for a given type, the system follows this fallback chain:
- Explicit deployment — The deployment ID set directly on the profile or interaction
- Connection default — The default deployment for the requested type on the connection
- Global default — The global default deployment configured in Settings > Artificial Intelligence > Default Deployments
- null — No deployment found
Automatic Migration
Most users don't need to do anything manually. The automatic migration handles the conversion on startup.
On application startup, the data migration automatically:
- Scans all existing
AIProviderConnectionrecords for deployment name fields - Creates typed
AIDeploymentrecords for each non-empty deployment name - Sets the
IsDefaultflag on the first deployment of each type per connection - Preserves all existing functionality — no downtime or data loss
After migration, review the auto-created deployments at Artificial Intelligence > Deployments to verify they look correct.
Manual Steps After Migration
After the automatic migration runs:
- Review deployments — Navigate to Artificial Intelligence > Deployments and verify the auto-created records have the correct types and default flags.
- Set global defaults — Go to Settings > Artificial Intelligence > Default Deployments and configure global defaults for Utility, Embedding, and Image deployment types. These serve as fallbacks when a profile doesn't specify a deployment.
- Update profiles (optional) — Existing profiles continue to work. However, you can now set separate
ChatDeploymentIdandUtilityDeploymentIdon each profile for more granular control.
appsettings.json Migration
Old Format (still supported, deprecated)
{
"OrchardCore": {
"CrestApps_AI": {
"Providers": {
"OpenAI": {
"Connections": {
"default": {
"ChatDeploymentName": "gpt-4o",
"UtilityDeploymentName": "gpt-4o-mini",
"EmbeddingDeploymentName": "text-embedding-3-small",
"ImagesDeploymentName": "dall-e-3"
}
}
}
}
}
}
}
New Format (recommended)
{
"OrchardCore": {
"CrestApps_AI": {
"Providers": {
"OpenAI": {
"Connections": {
"default": {
"Deployments": [
{
"Name": "gpt-4o",
"Type": "Chat",
"IsDefault": true
},
{
"Name": "gpt-4o-mini",
"Type": "Utility",
"IsDefault": true
},
{
"Name": "text-embedding-3-small",
"Type": "Embedding",
"IsDefault": true
},
{
"Name": "dall-e-3",
"Type": "Image",
"IsDefault": true
}
]
}
}
}
}
}
}
}
Both formats are supported simultaneously. If both are present, the Deployments array takes precedence. We recommend migrating to the new format when convenient.
Code Migration
Reading Deployment Names
If your code referenced deployment names from the connection:
// ❌ Old — deprecated
var chatDeployment = connection.ChatDeploymentName;
var embeddingDeployment = connection.EmbeddingDeploymentName;
// ✅ New — use IAIDeploymentManager
var chatDeployment = await deploymentManager.ResolveAsync(
AIDeploymentType.Chat, connectionName: connectionName);
var embeddingDeployment = await deploymentManager.ResolveAsync(
AIDeploymentType.Embedding, connectionName: connectionName);
AI Profile DeploymentId
If your code referenced DeploymentId on AI Profiles:
// ❌ Old
var deploymentId = profile.DeploymentId;
// ✅ New
var chatDeploymentId = profile.ChatDeploymentId;
var utilityDeploymentId = profile.UtilityDeploymentId;
AICompletionContext
If your code built or read AICompletionContext:
// ❌ Old
context.DeploymentId = "some-id";
// ✅ New
context.ChatDeploymentId = "some-id";
Recipe Migration
Old Recipe Format (still works)
{
"steps": [
{
"name": "AIProfile",
"profiles": [
{
"Name": "MyProfile",
"ConnectionName": "default",
"DeploymentId": "some-deployment-id",
...
}
]
}
]
}
New Recipe Format
{
"steps": [
{
"name": "AIProfile",
"profiles": [
{
"Name": "MyProfile",
"ConnectionName": "default",
"ChatDeploymentId": "chat-deployment-id",
"UtilityDeploymentId": "utility-deployment-id",
...
}
]
}
]
}
AI Deployment Recipes
Create typed deployments via recipes:
{
"steps": [
{
"name": "AIDeployment",
"deployments": [
{
"Name": "gpt-4o",
"ProviderName": "OpenAI",
"ConnectionName": "default",
"Type": "Chat",
"IsDefault": true
},
{
"Name": "gpt-4o-mini",
"ProviderName": "OpenAI",
"ConnectionName": "default",
"Type": "Utility",
"IsDefault": true
},
{
"Name": "dall-e-3",
"ProviderName": "OpenAI",
"ConnectionName": "default",
"Type": "Image",
"IsDefault": true
}
]
}
]
}
Summary of Deprecated Properties
| Deprecated Property | Replacement |
|---|---|
AIProviderConnection.ChatDeploymentName | AIDeployment record with Type = Chat |
AIProviderConnection.UtilityDeploymentName | AIDeployment record with Type = Utility |
AIProviderConnection.EmbeddingDeploymentName | AIDeployment record with Type = Embedding |
AIProviderConnection.ImagesDeploymentName | AIDeployment record with Type = Image |
AIProvider.DefaultChatDeploymentName | AIDeployment with IsDefault = true |
AIProvider.DefaultEmbeddingDeploymentName | AIDeployment with IsDefault = true |
AIProvider.DefaultUtilityDeploymentName | AIDeployment with IsDefault = true |
AIProvider.DefaultImagesDeploymentName | AIDeployment with IsDefault = true |
AIProfile.DeploymentId | AIProfile.ChatDeploymentId |
ChatInteraction.DeploymentId | ChatInteraction.ChatDeploymentId |
AICompletionContext.DeploymentId | AICompletionContext.ChatDeploymentId |
The deprecated properties still work for backward compatibility but will be removed in a future major release. Migrate to the new typed deployment system at your earliest convenience.