@jupyterlite/ai 0.6.2 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/lib/base-completer.d.ts +22 -5
- package/lib/base-completer.js +14 -1
- package/lib/chat-handler.d.ts +23 -11
- package/lib/chat-handler.js +66 -45
- package/lib/completion-provider.d.ts +2 -2
- package/lib/completion-provider.js +5 -4
- package/lib/components/stop-button.d.ts +0 -1
- package/lib/default-prompts.d.ts +2 -0
- package/lib/default-prompts.js +31 -0
- package/lib/default-providers/Anthropic/completer.d.ts +4 -11
- package/lib/default-providers/Anthropic/completer.js +5 -16
- package/lib/default-providers/ChromeAI/completer.d.ts +4 -11
- package/lib/default-providers/ChromeAI/completer.js +5 -16
- package/lib/default-providers/ChromeAI/instructions.d.ts +4 -0
- package/lib/default-providers/ChromeAI/instructions.js +18 -0
- package/lib/default-providers/ChromeAI/settings-schema.json +0 -3
- package/lib/default-providers/Gemini/completer.d.ts +12 -0
- package/lib/default-providers/Gemini/completer.js +48 -0
- package/lib/default-providers/Gemini/instructions.d.ts +2 -0
- package/lib/default-providers/Gemini/instructions.js +9 -0
- package/lib/default-providers/Gemini/settings-schema.json +64 -0
- package/lib/default-providers/MistralAI/completer.d.ts +10 -13
- package/lib/default-providers/MistralAI/completer.js +42 -52
- package/lib/default-providers/MistralAI/instructions.d.ts +1 -1
- package/lib/default-providers/MistralAI/instructions.js +2 -0
- package/lib/default-providers/Ollama/completer.d.ts +12 -0
- package/lib/default-providers/Ollama/completer.js +43 -0
- package/lib/default-providers/Ollama/instructions.d.ts +2 -0
- package/lib/default-providers/Ollama/instructions.js +70 -0
- package/lib/default-providers/Ollama/settings-schema.json +143 -0
- package/lib/default-providers/OpenAI/completer.d.ts +4 -11
- package/lib/default-providers/OpenAI/completer.js +8 -16
- package/lib/default-providers/OpenAI/settings-schema.json +88 -128
- package/lib/default-providers/WebLLM/completer.d.ts +21 -0
- package/lib/default-providers/WebLLM/completer.js +127 -0
- package/lib/default-providers/WebLLM/instructions.d.ts +6 -0
- package/lib/default-providers/WebLLM/instructions.js +32 -0
- package/lib/default-providers/WebLLM/settings-schema.json +19 -0
- package/lib/default-providers/index.js +127 -8
- package/lib/index.d.ts +3 -2
- package/lib/index.js +80 -36
- package/lib/provider.d.ts +48 -22
- package/lib/provider.js +254 -101
- package/lib/settings/index.d.ts +1 -1
- package/lib/settings/index.js +1 -1
- package/lib/settings/panel.d.ts +151 -14
- package/lib/settings/panel.js +334 -145
- package/lib/settings/textarea.d.ts +2 -0
- package/lib/settings/textarea.js +18 -0
- package/lib/tokens.d.ts +45 -22
- package/lib/tokens.js +2 -1
- package/lib/types/ai-model.d.ts +24 -0
- package/lib/types/ai-model.js +5 -0
- package/package.json +19 -15
- package/schema/chat.json +1 -1
- package/schema/provider-registry.json +8 -8
- package/schema/system-prompts.json +22 -0
- package/src/base-completer.ts +38 -6
- package/src/chat-handler.ts +62 -31
- package/src/completion-provider.ts +3 -3
- package/src/default-prompts.ts +33 -0
- package/src/default-providers/Anthropic/completer.ts +5 -21
- package/src/default-providers/ChromeAI/completer.ts +5 -21
- package/src/default-providers/ChromeAI/instructions.ts +21 -0
- package/src/default-providers/Gemini/completer.ts +61 -0
- package/src/default-providers/Gemini/instructions.ts +9 -0
- package/src/default-providers/MistralAI/completer.ts +47 -65
- package/src/default-providers/MistralAI/instructions.ts +2 -0
- package/src/default-providers/Ollama/completer.ts +54 -0
- package/src/default-providers/Ollama/instructions.ts +70 -0
- package/src/default-providers/OpenAI/completer.ts +8 -21
- package/src/default-providers/WebLLM/completer.ts +151 -0
- package/src/default-providers/WebLLM/instructions.ts +33 -0
- package/src/default-providers/index.ts +158 -18
- package/src/index.ts +108 -40
- package/src/provider.ts +300 -109
- package/src/settings/index.ts +1 -1
- package/src/settings/panel.tsx +463 -101
- package/src/settings/textarea.tsx +33 -0
- package/src/tokens.ts +49 -24
- package/src/types/ai-model.ts +37 -0
- package/src/types/service-worker.d.ts +6 -0
- package/style/base.css +34 -0
- package/lib/settings/settings-connector.d.ts +0 -31
- package/lib/settings/settings-connector.js +0 -61
- package/src/settings/settings-connector.ts +0 -88
|
@@ -1,26 +1,40 @@
|
|
|
1
|
+
import { Notification } from '@jupyterlab/apputils';
|
|
1
2
|
import { ChatAnthropic } from '@langchain/anthropic';
|
|
3
|
+
import { ChatWebLLM } from '@langchain/community/chat_models/webllm';
|
|
2
4
|
import { ChromeAI } from '@langchain/community/experimental/llms/chrome_ai';
|
|
5
|
+
import { ChatGoogleGenerativeAI } from '@langchain/google-genai';
|
|
3
6
|
import { ChatMistralAI } from '@langchain/mistralai';
|
|
7
|
+
import { ChatOllama } from '@langchain/ollama';
|
|
4
8
|
import { ChatOpenAI } from '@langchain/openai';
|
|
5
|
-
import { IAIProviderRegistry } from '../tokens';
|
|
6
9
|
// Import completers
|
|
7
10
|
import { AnthropicCompleter } from './Anthropic/completer';
|
|
8
11
|
import { ChromeCompleter } from './ChromeAI/completer';
|
|
12
|
+
import { GeminiCompleter } from './Gemini/completer';
|
|
9
13
|
import { CodestralCompleter } from './MistralAI/completer';
|
|
14
|
+
import { OllamaCompleter } from './Ollama/completer';
|
|
10
15
|
import { OpenAICompleter } from './OpenAI/completer';
|
|
16
|
+
import { WebLLMCompleter } from './WebLLM/completer';
|
|
11
17
|
// Import Settings
|
|
12
18
|
import AnthropicSettings from './Anthropic/settings-schema.json';
|
|
13
19
|
import ChromeAISettings from './ChromeAI/settings-schema.json';
|
|
20
|
+
import GeminiSettings from './Gemini/settings-schema.json';
|
|
14
21
|
import MistralAISettings from './MistralAI/settings-schema.json';
|
|
22
|
+
import OllamaAISettings from './Ollama/settings-schema.json';
|
|
15
23
|
import OpenAISettings from './OpenAI/settings-schema.json';
|
|
24
|
+
import WebLLMSettings from './WebLLM/settings-schema.json';
|
|
16
25
|
// Import instructions
|
|
17
|
-
import ChromeAIInstructions from './ChromeAI/instructions';
|
|
26
|
+
import ChromeAIInstructions, { compatibilityCheck as chromeAICompatibilityCheck } from './ChromeAI/instructions';
|
|
27
|
+
import GeminiInstructions from './Gemini/instructions';
|
|
18
28
|
import MistralAIInstructions from './MistralAI/instructions';
|
|
29
|
+
import OllamaInstructions from './Ollama/instructions';
|
|
30
|
+
import WebLLMInstructions, { compatibilityCheck as webLLMCompatibilityCheck } from './WebLLM/instructions';
|
|
31
|
+
import { prebuiltAppConfig } from '@mlc-ai/web-llm';
|
|
32
|
+
import { IAIProviderRegistry } from '../tokens';
|
|
19
33
|
// Build the AIProvider list
|
|
20
34
|
const AIProviders = [
|
|
21
35
|
{
|
|
22
36
|
name: 'Anthropic',
|
|
23
|
-
|
|
37
|
+
chat: ChatAnthropic,
|
|
24
38
|
completer: AnthropicCompleter,
|
|
25
39
|
settingsSchema: AnthropicSettings,
|
|
26
40
|
errorMessage: (error) => error.error.error.message
|
|
@@ -29,26 +43,127 @@ const AIProviders = [
|
|
|
29
43
|
name: 'ChromeAI',
|
|
30
44
|
// TODO: fix
|
|
31
45
|
// @ts-expect-error: missing properties
|
|
32
|
-
|
|
46
|
+
chat: ChromeAI,
|
|
33
47
|
completer: ChromeCompleter,
|
|
34
48
|
instructions: ChromeAIInstructions,
|
|
35
|
-
settingsSchema: ChromeAISettings
|
|
49
|
+
settingsSchema: ChromeAISettings,
|
|
50
|
+
compatibilityCheck: chromeAICompatibilityCheck
|
|
36
51
|
},
|
|
37
52
|
{
|
|
38
53
|
name: 'MistralAI',
|
|
39
|
-
|
|
54
|
+
chat: ChatMistralAI,
|
|
40
55
|
completer: CodestralCompleter,
|
|
41
56
|
instructions: MistralAIInstructions,
|
|
42
57
|
settingsSchema: MistralAISettings
|
|
43
58
|
},
|
|
59
|
+
{
|
|
60
|
+
name: 'Ollama',
|
|
61
|
+
chat: ChatOllama,
|
|
62
|
+
completer: OllamaCompleter,
|
|
63
|
+
instructions: OllamaInstructions,
|
|
64
|
+
settingsSchema: OllamaAISettings
|
|
65
|
+
},
|
|
66
|
+
{
|
|
67
|
+
name: 'Gemini',
|
|
68
|
+
chat: ChatGoogleGenerativeAI,
|
|
69
|
+
completer: GeminiCompleter,
|
|
70
|
+
instructions: GeminiInstructions,
|
|
71
|
+
settingsSchema: GeminiSettings
|
|
72
|
+
},
|
|
44
73
|
{
|
|
45
74
|
name: 'OpenAI',
|
|
46
|
-
|
|
75
|
+
chat: ChatOpenAI,
|
|
47
76
|
completer: OpenAICompleter,
|
|
48
77
|
settingsSchema: OpenAISettings
|
|
49
78
|
}
|
|
50
79
|
];
|
|
51
|
-
|
|
80
|
+
/**
|
|
81
|
+
* Register the WebLLM provider in a separate plugin since it creates notifications
|
|
82
|
+
* when the model is changed in the settings.
|
|
83
|
+
*/
|
|
84
|
+
const webLLMProviderPlugin = {
|
|
85
|
+
id: '@jupyterlite/ai:webllm',
|
|
86
|
+
description: 'Register the WebLLM provider',
|
|
87
|
+
autoStart: true,
|
|
88
|
+
requires: [IAIProviderRegistry],
|
|
89
|
+
activate: (app, registry) => {
|
|
90
|
+
registry.add({
|
|
91
|
+
name: 'WebLLM',
|
|
92
|
+
chat: ChatWebLLM,
|
|
93
|
+
completer: WebLLMCompleter,
|
|
94
|
+
settingsSchema: WebLLMSettings,
|
|
95
|
+
instructions: WebLLMInstructions,
|
|
96
|
+
compatibilityCheck: webLLMCompatibilityCheck,
|
|
97
|
+
exposeChatModel: true
|
|
98
|
+
});
|
|
99
|
+
registry.providerChanged.connect(async (sender, role) => {
|
|
100
|
+
const { currentChatModel } = registry;
|
|
101
|
+
// TODO: implement a proper way to handle models that may need to be initialized before being used.
|
|
102
|
+
// Mostly applies to WebLLM and ChromeAI as they may need to download the model in the browser first.
|
|
103
|
+
if (registry.currentName(role) === 'WebLLM') {
|
|
104
|
+
// Leaving this check here, but it should never happen, this check is done in
|
|
105
|
+
// the provider registry, and the current name is set to 'None' if there is a
|
|
106
|
+
// compatibility error.
|
|
107
|
+
const compatibilityError = await webLLMCompatibilityCheck();
|
|
108
|
+
if (compatibilityError) {
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
111
|
+
const model = currentChatModel;
|
|
112
|
+
if (model === null || !model.model) {
|
|
113
|
+
return;
|
|
114
|
+
}
|
|
115
|
+
// Find if the model is part of the prebuiltAppConfig
|
|
116
|
+
const modelRecord = prebuiltAppConfig.model_list.find(modelRecord => modelRecord.model_id === model.model);
|
|
117
|
+
if (!modelRecord) {
|
|
118
|
+
Notification.dismiss();
|
|
119
|
+
Notification.emit(`Model ${model.model} not found in the prebuiltAppConfig`, 'error', {
|
|
120
|
+
autoClose: 2000
|
|
121
|
+
});
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
// create a notification
|
|
125
|
+
const notification = Notification.emit('Loading model...', 'in-progress', {
|
|
126
|
+
autoClose: false,
|
|
127
|
+
progress: 0
|
|
128
|
+
});
|
|
129
|
+
try {
|
|
130
|
+
void model.initialize(report => {
|
|
131
|
+
const { progress, text } = report;
|
|
132
|
+
if (progress === 1) {
|
|
133
|
+
Notification.update({
|
|
134
|
+
id: notification,
|
|
135
|
+
progress: 1,
|
|
136
|
+
message: `Model ${model.model} loaded successfully`,
|
|
137
|
+
type: 'success',
|
|
138
|
+
autoClose: 2000
|
|
139
|
+
});
|
|
140
|
+
return;
|
|
141
|
+
}
|
|
142
|
+
Notification.update({
|
|
143
|
+
id: notification,
|
|
144
|
+
progress: progress / 1,
|
|
145
|
+
message: text,
|
|
146
|
+
type: 'in-progress'
|
|
147
|
+
});
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
catch (err) {
|
|
151
|
+
Notification.update({
|
|
152
|
+
id: notification,
|
|
153
|
+
progress: 1,
|
|
154
|
+
message: `Error loading model ${model.model}`,
|
|
155
|
+
type: 'error',
|
|
156
|
+
autoClose: 2000
|
|
157
|
+
});
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
});
|
|
161
|
+
}
|
|
162
|
+
};
|
|
163
|
+
/**
|
|
164
|
+
* Register all default AI providers.
|
|
165
|
+
*/
|
|
166
|
+
const aiProviderPlugins = AIProviders.map(provider => {
|
|
52
167
|
return {
|
|
53
168
|
id: `@jupyterlite/ai:${provider.name}`,
|
|
54
169
|
autoStart: true,
|
|
@@ -58,3 +173,7 @@ export const defaultProviderPlugins = AIProviders.map(provider => {
|
|
|
58
173
|
}
|
|
59
174
|
};
|
|
60
175
|
});
|
|
176
|
+
export const defaultProviderPlugins = [
|
|
177
|
+
webLLMProviderPlugin,
|
|
178
|
+
...aiProviderPlugins
|
|
179
|
+
];
|
package/lib/index.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { IChatCommandRegistry } from '@jupyter/chat';
|
|
2
2
|
import { JupyterFrontEndPlugin } from '@jupyterlab/application';
|
|
3
|
-
import { ISettingConnector } from '@jupyterlab/settingregistry';
|
|
4
3
|
import { IAIProviderRegistry } from './tokens';
|
|
5
|
-
declare const _default: (JupyterFrontEndPlugin<void> | JupyterFrontEndPlugin<IChatCommandRegistry> | JupyterFrontEndPlugin<IAIProviderRegistry>
|
|
4
|
+
declare const _default: (JupyterFrontEndPlugin<void> | JupyterFrontEndPlugin<IChatCommandRegistry> | JupyterFrontEndPlugin<IAIProviderRegistry>)[];
|
|
6
5
|
export default _default;
|
|
6
|
+
export { IAIProviderRegistry } from './tokens';
|
|
7
|
+
export * from './base-completer';
|
package/lib/index.js
CHANGED
|
@@ -1,16 +1,17 @@
|
|
|
1
1
|
import { ActiveCellManager, buildChatSidebar, buildErrorWidget, ChatCommandRegistry, IChatCommandRegistry, InputToolbarRegistry } from '@jupyter/chat';
|
|
2
|
+
import { ILayoutRestorer } from '@jupyterlab/application';
|
|
2
3
|
import { IThemeManager } from '@jupyterlab/apputils';
|
|
3
4
|
import { ICompletionProviderManager } from '@jupyterlab/completer';
|
|
4
5
|
import { INotebookTracker } from '@jupyterlab/notebook';
|
|
5
6
|
import { IRenderMimeRegistry } from '@jupyterlab/rendermime';
|
|
6
|
-
import {
|
|
7
|
+
import { ISettingRegistry } from '@jupyterlab/settingregistry';
|
|
7
8
|
import { IFormRendererRegistry } from '@jupyterlab/ui-components';
|
|
8
9
|
import { ISecretsManager, SecretsManager } from 'jupyter-secrets-manager';
|
|
9
|
-
import { ChatHandler } from './chat-handler';
|
|
10
|
+
import { ChatHandler, welcomeMessage } from './chat-handler';
|
|
10
11
|
import { CompletionProvider } from './completion-provider';
|
|
11
12
|
import { defaultProviderPlugins } from './default-providers';
|
|
12
13
|
import { AIProviderRegistry } from './provider';
|
|
13
|
-
import { aiSettingsRenderer,
|
|
14
|
+
import { aiSettingsRenderer, textArea } from './settings';
|
|
14
15
|
import { IAIProviderRegistry, PLUGIN_IDS } from './tokens';
|
|
15
16
|
import { stopItem } from './components/stop-button';
|
|
16
17
|
const chatCommandRegistryPlugin = {
|
|
@@ -29,8 +30,13 @@ const chatPlugin = {
|
|
|
29
30
|
description: 'LLM chat extension',
|
|
30
31
|
autoStart: true,
|
|
31
32
|
requires: [IAIProviderRegistry, IRenderMimeRegistry, IChatCommandRegistry],
|
|
32
|
-
optional: [
|
|
33
|
-
|
|
33
|
+
optional: [
|
|
34
|
+
INotebookTracker,
|
|
35
|
+
ISettingRegistry,
|
|
36
|
+
IThemeManager,
|
|
37
|
+
ILayoutRestorer
|
|
38
|
+
],
|
|
39
|
+
activate: async (app, providerRegistry, rmRegistry, chatCommandRegistry, notebookTracker, settingsRegistry, themeManager, restorer) => {
|
|
34
40
|
let activeCellManager = null;
|
|
35
41
|
if (notebookTracker) {
|
|
36
42
|
activeCellManager = new ActiveCellManager({
|
|
@@ -54,7 +60,7 @@ const chatPlugin = {
|
|
|
54
60
|
chatHandler.config = { sendWithShiftEnter, enableCodeToolbar };
|
|
55
61
|
chatHandler.personaName = personaName;
|
|
56
62
|
}
|
|
57
|
-
Promise.all([app.restored, settingsRegistry
|
|
63
|
+
Promise.all([app.restored, settingsRegistry?.load(chatPlugin.id)])
|
|
58
64
|
.then(([, settings]) => {
|
|
59
65
|
if (!settings) {
|
|
60
66
|
console.warn('The SettingsRegistry is not loaded for the chat extension');
|
|
@@ -70,8 +76,8 @@ const chatPlugin = {
|
|
|
70
76
|
const inputToolbarRegistry = InputToolbarRegistry.defaultToolbarRegistry();
|
|
71
77
|
const stopButton = stopItem(() => chatHandler.stopStreaming());
|
|
72
78
|
inputToolbarRegistry.addItem('stop', stopButton);
|
|
73
|
-
chatHandler.writersChanged.connect((_,
|
|
74
|
-
if (
|
|
79
|
+
chatHandler.writersChanged.connect((_, writers) => {
|
|
80
|
+
if (writers.filter(writer => writer.user.username === chatHandler.personaName).length) {
|
|
75
81
|
inputToolbarRegistry.hide('send');
|
|
76
82
|
inputToolbarRegistry.show('stop');
|
|
77
83
|
}
|
|
@@ -86,15 +92,19 @@ const chatPlugin = {
|
|
|
86
92
|
themeManager,
|
|
87
93
|
rmRegistry,
|
|
88
94
|
chatCommandRegistry,
|
|
89
|
-
inputToolbarRegistry
|
|
95
|
+
inputToolbarRegistry,
|
|
96
|
+
welcomeMessage: welcomeMessage(providerRegistry.providers)
|
|
90
97
|
});
|
|
91
|
-
chatWidget.title.caption = 'Jupyterlite AI Chat';
|
|
92
98
|
}
|
|
93
99
|
catch (e) {
|
|
94
100
|
chatWidget = buildErrorWidget(themeManager);
|
|
95
101
|
}
|
|
102
|
+
chatWidget.title.caption = 'Jupyterlite AI Chat';
|
|
103
|
+
chatWidget.id = '@jupyterlite/ai:chat-widget';
|
|
96
104
|
app.shell.add(chatWidget, 'left', { rank: 2000 });
|
|
97
|
-
|
|
105
|
+
if (restorer) {
|
|
106
|
+
restorer.add(chatWidget, chatWidget.id);
|
|
107
|
+
}
|
|
98
108
|
}
|
|
99
109
|
};
|
|
100
110
|
const completerPlugin = {
|
|
@@ -113,33 +123,43 @@ const providerRegistryPlugin = SecretsManager.sign(PLUGIN_IDS.providerRegistry,
|
|
|
113
123
|
id: PLUGIN_IDS.providerRegistry,
|
|
114
124
|
autoStart: true,
|
|
115
125
|
requires: [IFormRendererRegistry, ISettingRegistry],
|
|
116
|
-
optional: [IRenderMimeRegistry, ISecretsManager
|
|
126
|
+
optional: [IRenderMimeRegistry, ISecretsManager],
|
|
117
127
|
provides: IAIProviderRegistry,
|
|
118
|
-
activate: (app, editorRegistry, settingRegistry, rmRegistry, secretsManager
|
|
128
|
+
activate: (app, editorRegistry, settingRegistry, rmRegistry, secretsManager) => {
|
|
119
129
|
const providerRegistry = new AIProviderRegistry({
|
|
120
130
|
token,
|
|
121
131
|
secretsManager
|
|
122
132
|
});
|
|
123
|
-
editorRegistry.addRenderer(`${PLUGIN_IDS.providerRegistry}.
|
|
133
|
+
editorRegistry.addRenderer(`${PLUGIN_IDS.providerRegistry}.AIproviders`, aiSettingsRenderer({
|
|
124
134
|
providerRegistry,
|
|
125
135
|
secretsToken: token,
|
|
126
136
|
rmRegistry,
|
|
127
|
-
secretsManager
|
|
128
|
-
settingConnector
|
|
137
|
+
secretsManager
|
|
129
138
|
}));
|
|
130
139
|
settingRegistry
|
|
131
140
|
.load(providerRegistryPlugin.id)
|
|
132
141
|
.then(settings => {
|
|
142
|
+
if (!secretsManager) {
|
|
143
|
+
delete settings.schema.properties?.['UseSecretsManager'];
|
|
144
|
+
}
|
|
133
145
|
const updateProvider = () => {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
146
|
+
// Get the Ai provider settings.
|
|
147
|
+
const providerSettings = settings.get('AIproviders')
|
|
148
|
+
.composite;
|
|
149
|
+
// Update completer provider.
|
|
150
|
+
if (Object.keys(providerSettings).includes('completer')) {
|
|
151
|
+
providerRegistry.setCompleterProvider(providerSettings['completer']);
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
providerRegistry.setCompleterProvider({});
|
|
155
|
+
}
|
|
156
|
+
// Update chat provider.
|
|
157
|
+
if (Object.keys(providerSettings).includes('chat')) {
|
|
158
|
+
providerRegistry.setChatProvider(providerSettings['chat']);
|
|
159
|
+
}
|
|
160
|
+
else {
|
|
161
|
+
providerRegistry.setChatProvider({});
|
|
162
|
+
}
|
|
143
163
|
};
|
|
144
164
|
settings.changed.connect(() => updateProvider());
|
|
145
165
|
updateProvider();
|
|
@@ -150,23 +170,47 @@ const providerRegistryPlugin = SecretsManager.sign(PLUGIN_IDS.providerRegistry,
|
|
|
150
170
|
return providerRegistry;
|
|
151
171
|
}
|
|
152
172
|
}));
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
* implementations that may want to fetch settings from a different source or
|
|
156
|
-
* endpoint.
|
|
157
|
-
*/
|
|
158
|
-
const settingsConnector = {
|
|
159
|
-
id: PLUGIN_IDS.settingsConnector,
|
|
160
|
-
description: 'Provides a settings connector which does not save passwords.',
|
|
173
|
+
const systemPromptsPlugin = {
|
|
174
|
+
id: PLUGIN_IDS.systemPrompts,
|
|
161
175
|
autoStart: true,
|
|
162
|
-
|
|
163
|
-
|
|
176
|
+
requires: [IAIProviderRegistry, ISettingRegistry],
|
|
177
|
+
optional: [IFormRendererRegistry],
|
|
178
|
+
activate: (app, providerRegistry, settingsRegistry, editorRegistry) => {
|
|
179
|
+
// Set textarea renderer for the prompt setting.
|
|
180
|
+
editorRegistry?.addRenderer(`${PLUGIN_IDS.systemPrompts}.chatSystemPrompt`, textArea);
|
|
181
|
+
editorRegistry?.addRenderer(`${PLUGIN_IDS.systemPrompts}.completionSystemPrompt`, textArea);
|
|
182
|
+
/**
|
|
183
|
+
* Update the prompts in the provider registry.
|
|
184
|
+
*/
|
|
185
|
+
function loadSetting(setting) {
|
|
186
|
+
providerRegistry.chatSystemPrompt = setting.get('chatSystemPrompt')
|
|
187
|
+
.composite;
|
|
188
|
+
providerRegistry.completerSystemPrompt = setting.get('completionSystemPrompt').composite;
|
|
189
|
+
}
|
|
190
|
+
Promise.all([
|
|
191
|
+
app.restored,
|
|
192
|
+
settingsRegistry?.load(PLUGIN_IDS.systemPrompts)
|
|
193
|
+
])
|
|
194
|
+
.then(([, settings]) => {
|
|
195
|
+
if (!settings) {
|
|
196
|
+
console.warn('The SettingsRegistry is not loaded for the chat extension');
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
loadSetting(settings);
|
|
200
|
+
settings.changed.connect(loadSetting);
|
|
201
|
+
})
|
|
202
|
+
.catch(reason => {
|
|
203
|
+
console.error(`Something went wrong when reading the settings.\n${reason}`);
|
|
204
|
+
});
|
|
205
|
+
}
|
|
164
206
|
};
|
|
165
207
|
export default [
|
|
166
208
|
providerRegistryPlugin,
|
|
167
209
|
chatCommandRegistryPlugin,
|
|
168
210
|
chatPlugin,
|
|
169
211
|
completerPlugin,
|
|
170
|
-
|
|
212
|
+
systemPromptsPlugin,
|
|
171
213
|
...defaultProviderPlugins
|
|
172
214
|
];
|
|
215
|
+
export { IAIProviderRegistry } from './tokens';
|
|
216
|
+
export * from './base-completer';
|
package/lib/provider.d.ts
CHANGED
|
@@ -1,13 +1,10 @@
|
|
|
1
1
|
import { BaseLanguageModel } from '@langchain/core/language_models/base';
|
|
2
|
-
import { BaseChatModel } from '@langchain/core/language_models/chat_models';
|
|
3
|
-
import { ISignal } from '@lumino/signaling';
|
|
4
2
|
import { ReadonlyPartialJSONObject } from '@lumino/coreutils';
|
|
3
|
+
import { ISignal } from '@lumino/signaling';
|
|
5
4
|
import { JSONSchema7 } from 'json-schema';
|
|
6
5
|
import { ISecretsManager } from 'jupyter-secrets-manager';
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
export declare const chatSystemPrompt: (options: AIProviderRegistry.IPromptOptions) => string;
|
|
10
|
-
export declare const COMPLETION_SYSTEM_PROMPT = "\nYou are an application built to provide helpful code completion suggestions.\nYou should only produce code. Keep comments to minimum, use the\nprogramming language comment syntax. Produce clean code.\nThe code is written in JupyterLab, a data analysis and code development\nenvironment which can execute code extended with additional syntax for\ninteractive features, such as magics.\nOnly give raw strings back, do not format the response using backticks.\nThe output should be a single string, and should correspond to what a human users\nwould write.\nDo not include the prompt in the output, only the string that should be appended to the current input.\n";
|
|
6
|
+
import { IAIProvider, IAIProviderRegistry, ModelRole } from './tokens';
|
|
7
|
+
import { AIChatModel, AICompleter } from './types/ai-model';
|
|
11
8
|
export declare class AIProviderRegistry implements IAIProviderRegistry {
|
|
12
9
|
/**
|
|
13
10
|
* The constructor of the provider registry.
|
|
@@ -24,15 +21,25 @@ export declare class AIProviderRegistry implements IAIProviderRegistry {
|
|
|
24
21
|
/**
|
|
25
22
|
* Get the current provider name.
|
|
26
23
|
*/
|
|
27
|
-
|
|
24
|
+
currentName(role: ModelRole): string;
|
|
25
|
+
/**
|
|
26
|
+
* Get the current AICompleter.
|
|
27
|
+
*/
|
|
28
|
+
get currentCompleter(): AICompleter | null;
|
|
28
29
|
/**
|
|
29
|
-
*
|
|
30
|
+
* Getter/setter for the completer system prompt.
|
|
30
31
|
*/
|
|
31
|
-
get
|
|
32
|
+
get completerSystemPrompt(): string;
|
|
33
|
+
set completerSystemPrompt(value: string);
|
|
32
34
|
/**
|
|
33
|
-
* Get the current
|
|
35
|
+
* Get the current AIChatModel.
|
|
34
36
|
*/
|
|
35
|
-
get currentChatModel():
|
|
37
|
+
get currentChatModel(): AIChatModel | null;
|
|
38
|
+
/**
|
|
39
|
+
* Getter/setter for the chat system prompt.
|
|
40
|
+
*/
|
|
41
|
+
get chatSystemPrompt(): string;
|
|
42
|
+
set chatSystemPrompt(value: string);
|
|
36
43
|
/**
|
|
37
44
|
* Get the settings schema of a given provider.
|
|
38
45
|
*/
|
|
@@ -41,39 +48,58 @@ export declare class AIProviderRegistry implements IAIProviderRegistry {
|
|
|
41
48
|
* Get the instructions of a given provider.
|
|
42
49
|
*/
|
|
43
50
|
getInstructions(provider: string): string | undefined;
|
|
51
|
+
/**
|
|
52
|
+
* Get the compatibility check function of a given provider.
|
|
53
|
+
*/
|
|
54
|
+
getCompatibilityCheck(provider: string): (() => Promise<string | null>) | undefined;
|
|
44
55
|
/**
|
|
45
56
|
* Format an error message from the current provider.
|
|
46
57
|
*/
|
|
47
58
|
formatErrorMessage(error: any): string;
|
|
48
59
|
/**
|
|
49
|
-
* Get the current chat error;
|
|
60
|
+
* Get/set the current chat error;
|
|
50
61
|
*/
|
|
51
62
|
get chatError(): string;
|
|
63
|
+
private set chatError(value);
|
|
52
64
|
/**
|
|
53
|
-
*
|
|
65
|
+
* Get/set the current completer error.
|
|
54
66
|
*/
|
|
55
67
|
get completerError(): string;
|
|
68
|
+
private set completerError(value);
|
|
56
69
|
/**
|
|
57
|
-
*
|
|
58
|
-
|
|
70
|
+
* A function to emit a notification error.
|
|
71
|
+
*/
|
|
72
|
+
private _emitErrorNotification;
|
|
73
|
+
/**
|
|
74
|
+
* Set the completer provider.
|
|
75
|
+
* Creates the provider if the name has changed, otherwise only updates its config.
|
|
76
|
+
*
|
|
77
|
+
* @param options - An object with the name and the settings of the provider to use.
|
|
78
|
+
*/
|
|
79
|
+
setCompleterProvider(settings: ReadonlyPartialJSONObject): Promise<void>;
|
|
80
|
+
/**
|
|
81
|
+
* Set the chat provider.
|
|
82
|
+
* Creates the provider if the name has changed, otherwise only updates its config.
|
|
59
83
|
*
|
|
60
84
|
* @param options - An object with the name and the settings of the provider to use.
|
|
61
85
|
*/
|
|
62
|
-
|
|
86
|
+
setChatProvider(settings: ReadonlyPartialJSONObject): Promise<void>;
|
|
63
87
|
/**
|
|
64
88
|
* A signal emitting when the provider or its settings has changed.
|
|
65
89
|
*/
|
|
66
|
-
get providerChanged(): ISignal<IAIProviderRegistry,
|
|
90
|
+
get providerChanged(): ISignal<IAIProviderRegistry, ModelRole>;
|
|
91
|
+
/**
|
|
92
|
+
* Build a new settings object containing the secrets.
|
|
93
|
+
*/
|
|
94
|
+
private _buildFullSettings;
|
|
67
95
|
private _secretsManager;
|
|
68
|
-
private _currentProvider;
|
|
69
|
-
private _completer;
|
|
70
|
-
private _chatModel;
|
|
71
|
-
private _name;
|
|
72
96
|
private _providerChanged;
|
|
73
97
|
private _chatError;
|
|
74
98
|
private _completerError;
|
|
75
|
-
private
|
|
99
|
+
private _notifications;
|
|
76
100
|
private _deferredProvider;
|
|
101
|
+
private _chatPrompt;
|
|
102
|
+
private _completerPrompt;
|
|
77
103
|
}
|
|
78
104
|
export declare namespace AIProviderRegistry {
|
|
79
105
|
/**
|