chatSelectedModel.ts ×9

Frontier kind: Code frontier

unlabeled · c_9a81f00e4567

36 tests · 29382 LOC · 143 files · introduces 0 tests · 106 LOC · 1 file

Introduces — evidence that enters the hierarchy at this concept

Code
9 ranges106 lines · 1 files
Tests
0 tests

Contains — complete concept membership

All code (extent)
2830 ranges29382 lines · 143 files · Browse complete extent
All tests (intent)
36 testsBrowse complete intent

Neighbourhood graph

The orange circle is the focus. Violet and green circles are every ancestor and descendant, broader and narrower, at any distance; blue squares and pink diamonds are the introduced files and exact introduced tests of every visible concept, not only the focus's. Arrows point from broader to narrower concepts and bridge only concepts omitted from this view. Undirected links show source or test introduction. Concept and file size follows LOC; exact test nodes use test-count units.

Introduced files, introduced tests, and structurally relevant concept specialization

In the embedded map, ordinary wheel input scrolls the page; use the visible controls to zoom and drag to pan. Open the full-screen map for canvas navigation: wheel pans, Ctrl/Command plus wheel zooms, and arrow keys pan when this region is focused. On touch screens, open the full-screen map to pan or pinch. If JavaScript or WebGL is unavailable, use the native relationship evidence on this page.

Graph controls are ready.

Interactive rendering requires JavaScript and WebGL. Use the native relationship evidence on this page while the interactive map is unavailable.

Native relationship evidence

Every exact file and test below is linked only from the concept that introduces it.

Introduced tests

Every collected test enters the hierarchy at exactly one concept.

No tests are introduced at this concept. Its intent tests are introduced by other concepts.

Introduced code

Every collected source range enters the hierarchy at exactly one concept.

1 file ranked by introduced lines: 106 introduced LOC across 9 ranges. Expand a file to inspect source; the > gutter marks introduced lines.

src/vs/workbench/contrib/chat/common/chatSelectedModel.ts 106 introduced LOC · 9 ranges

Open complete file

1 > /*--------------------------------------------------------------------------------------------- chatSelectedModel.ts
2 > * Copyright (c) Microsoft Corporation. All rights reserved.
3 > * Licensed under the MIT License. See License.txt in the project root for license information.
4 > *--------------------------------------------------------------------------------------------*/
5 >
6 > import { IContextKeyService } from '../../../../platform/contextkey/common/contextkey.js';
7 > import { IStorageService, StorageScope, StorageTarget } from '../../../../platform/storage/common/storage.js';
8 > import { ChatContextKeys } from './actions/chatContextKeys.js';
9 > import { COPILOT_VENDOR_ID, ILanguageModelChatMetadata, ILanguageModelsService } from './languageModels.js';
10 >
11 > /**
12 > * Storage key prefix for persisted model selections.
13 > * Full key format: `chat.currentLanguageModel.{location}[.{modelTarget}]`
14 > */
15 > export const SELECTED_MODEL_STORAGE_KEY_PREFIX = 'chat.currentLanguageModel.';
16 >
17 > export const SELECTED_MODEL_STORAGE_SCOPE = StorageScope.PROFILE;
18 > export const SELECTED_MODEL_STORAGE_TARGET = StorageTarget.USER;
19 >
20 > /**
21 > * Builds the storage key used to persist the selected language model for a
22 > * given chat location and optional model target.
23 > *
24 > * Shared by model-selection surfaces so they can read and write the explicit
25 > * remembered preference without depending on widget internals.
26 > */
27 > export function getSelectedModelStorageKey(location: string, modelTarget?: string): string {
28 if (modelTarget) {
29 return `${SELECTED_MODEL_STORAGE_KEY_PREFIX}${location}.${modelTarget}`;
31 return `${SELECTED_MODEL_STORAGE_KEY_PREFIX}${location}`;
32 }
34 > export function storeSelectedModel(
35 storageService: IStorageService,
36 location: string,
40 storageService.store(getSelectedModelStorageKey(location, modelTarget), identifier, SELECTED_MODEL_STORAGE_SCOPE, SELECTED_MODEL_STORAGE_TARGET);
41 }
43 > /** Reads the selected model and lazily migrates the previous application-scoped value. */
44 > export function getStoredSelectedModel(
45 storageService: IStorageService,
46 location: string,
75 return legacyIdentifier;
76 }
78 > /**
79 > * Resolves the currently selected chat model identifier using a two-step
80 > * strategy:
81 > *
82 > * 1. Read the `chatModelId` context key (set when a chat widget is active).
83 > * 2. Fall back to the persisted explicit model preference.
84 > *
85 > * Returns the raw model identifier string (may include a vendor prefix like
86 > * `"copilot/gpt-4.1"` from storage, or a short id like `"gpt-4.1"` from
87 > * the context key), or `undefined` if no selection is available.
88 > */
89 > export function getSelectedModelIdentifier(
90 contextKeyService: IContextKeyService,
91 storageService: IStorageService,
100 return getPersistedSelectedModelIdentifier(contextKeyService, storageService);
101 }
103 > /**
104 > * Reads the persisted, fully-qualified model identifier written by a model
105 > * selection surface (e.g. `"copilot/gpt-4.1"` or `"customendpoint/ANT/gpt-4.1"`).
106 > *
107 > * Unlike the `chatModelId` context key (which holds only the short, lower-cased
108 > * model id), the persisted identifier carries the vendor and therefore
109 > * disambiguates the same model served via BYOK vs CAPI. Returns `undefined`
110 > * when no selection has been persisted.
111 > */
112 > export function getPersistedSelectedModelIdentifier(
113 contextKeyService: IContextKeyService,
114 storageService: IStorageService,
129 return undefined;
130 }
132 > /**
133 > * Resolves the registered metadata of the currently selected chat model.
134 > *
135 > * The selected identifier may be a fully-qualified id (e.g. `"copilot/gpt-4.1"`
136 > * from persisted storage) or a short, lower-cased model id (e.g. `"gpt-4.1"`
137 > * from the `chatModelId` context key, which is set to `metadata.id`). The short
138 > * id cannot disambiguate the same model served via BYOK vs CAPI, so when a
139 > * direct registry lookup fails we fall back to the persisted, fully-qualified
140 > * identifier (which carries the vendor) rather than matching on the short id.
141 > *
142 > * Returns `undefined` when no model is selected or the selection cannot be
143 > * resolved to a registered model (e.g. the provider has not been activated
144 > * yet); callers that only need the vendor can fall back to
145 > * {@link getSelectedModelVendor}.
146 > */
147 > export function getSelectedModelMetadata(
148 contextKeyService: IContextKeyService,
149 storageService: IStorageService,
172 return undefined;
173 }
175 > /**
176 > * Resolves the vendor of the currently selected chat model.
177 > *
178 > * Tries the language model registry first (authoritative when models are
179 > * registered), then falls back to extracting the vendor prefix from the
180 > * persisted model identifier (e.g. `"copilot/gpt-4.1"` → `"copilot"`).
181 > *
182 > * Returns `undefined` if no model selection is available.
183 > */
184 > export function getSelectedModelVendor(
185 contextKeyService: IContextKeyService,
186 storageService: IStorageService,
201 return undefined;
202 }
204 > /**
205 > * Returns whether the given model is a "bring your own key" (BYOK) model.
206 > *
207 > * BYOK models are served using user-supplied credentials and are flagged as
208 > * such by their provider via {@link ILanguageModelChatMetadata.isBYOK}. All
209 > * other models (built-in Copilot, Copilot/Claude CLI, and agent-host models)
210 > * are served through the Copilot (CAPI) service and are therefore not BYOK.
211 > */
212 > export function isByokModel(metadata: ILanguageModelChatMetadata): boolean {
213 return metadata.isBYOK === true;
214 }
216 > /**
217 > * Returns whether the currently selected chat model is a Copilot model
218 > * (i.e. not BYOK).
219 > *
220 > * When the selection resolves to registered metadata this is the inverse of
221 > * {@link isByokModel}, so agent-host (CAPI-backed) models count as Copilot.
222 > * When no model is selected yet (widget not initialized) this returns `true`
223 > * so quota-style surfaces treat the unknown case as Copilot. As a last
224 > * resort, an unregistered selection is classified by its vendor prefix.
225 > */
226 > export function isSelectedModelCopilot(
227 contextKeyService: IContextKeyService,
228 storageService: IStorageService,