@theia/ai-chat 1.57.1 → 1.58.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/lib/browser/ai-chat-frontend-module.d.ts.map +1 -1
- package/lib/browser/ai-chat-frontend-module.js +14 -4
- package/lib/browser/ai-chat-frontend-module.js.map +1 -1
- package/lib/browser/change-set-file-element.d.ts +44 -0
- package/lib/browser/change-set-file-element.d.ts.map +1 -0
- package/lib/browser/change-set-file-element.js +113 -0
- package/lib/browser/change-set-file-element.js.map +1 -0
- package/lib/browser/change-set-file-resource.d.ts +13 -0
- package/lib/browser/change-set-file-resource.d.ts.map +1 -0
- package/lib/browser/change-set-file-resource.js +73 -0
- package/lib/browser/change-set-file-resource.js.map +1 -0
- package/lib/browser/change-set-file-service.d.ts +26 -0
- package/lib/browser/change-set-file-service.d.ts.map +1 -0
- package/lib/browser/change-set-file-service.js +139 -0
- package/lib/browser/change-set-file-service.js.map +1 -0
- package/lib/common/chat-agents.d.ts +4 -5
- package/lib/common/chat-agents.d.ts.map +1 -1
- package/lib/common/chat-agents.js +14 -21
- package/lib/common/chat-agents.js.map +1 -1
- package/lib/common/chat-model.d.ts +73 -7
- package/lib/common/chat-model.d.ts.map +1 -1
- package/lib/common/chat-model.js +123 -8
- package/lib/common/chat-model.js.map +1 -1
- package/lib/common/chat-service.d.ts +6 -0
- package/lib/common/chat-service.d.ts.map +1 -1
- package/lib/common/chat-service.js +12 -0
- package/lib/common/chat-service.js.map +1 -1
- package/lib/common/chat-tool-request-service.d.ts +17 -0
- package/lib/common/chat-tool-request-service.d.ts.map +1 -0
- package/lib/common/chat-tool-request-service.js +52 -0
- package/lib/common/chat-tool-request-service.js.map +1 -0
- package/lib/common/command-chat-agents.js +1 -1
- package/lib/common/command-chat-agents.js.map +1 -1
- package/package.json +10 -8
- package/src/browser/ai-chat-frontend-module.ts +17 -6
- package/src/browser/change-set-file-element.ts +137 -0
- package/src/browser/change-set-file-resource.ts +74 -0
- package/src/browser/change-set-file-service.ts +136 -0
- package/src/common/chat-agents.ts +12 -24
- package/src/common/chat-model.ts +193 -14
- package/src/common/chat-service.ts +17 -0
- package/src/common/chat-tool-request-service.ts +59 -0
- package/src/common/command-chat-agents.ts +1 -1
- package/lib/common/o1-chat-agent.d.ts +0 -13
- package/lib/common/o1-chat-agent.d.ts.map +0 -1
- package/lib/common/o1-chat-agent.js +0 -45
- package/lib/common/o1-chat-agent.js.map +0 -1
- package/src/common/o1-chat-agent.ts +0 -51
|
@@ -38,12 +38,11 @@ import {
|
|
|
38
38
|
LanguageModelStreamResponsePart,
|
|
39
39
|
MessageActor,
|
|
40
40
|
} from '@theia/ai-core/lib/common';
|
|
41
|
-
import { CancellationToken,
|
|
41
|
+
import { CancellationToken, ContributionProvider, ILogger, isArray } from '@theia/core';
|
|
42
42
|
import { inject, injectable, named, postConstruct, unmanaged } from '@theia/core/shared/inversify';
|
|
43
43
|
import { ChatAgentService } from './chat-agent-service';
|
|
44
44
|
import {
|
|
45
45
|
ChatModel,
|
|
46
|
-
ChatRequestModel,
|
|
47
46
|
ChatRequestModelImpl,
|
|
48
47
|
ChatResponseContent,
|
|
49
48
|
ErrorChatResponseContentImpl,
|
|
@@ -53,6 +52,7 @@ import {
|
|
|
53
52
|
import { findFirstMatch, parseContents } from './parse-contents';
|
|
54
53
|
import { DefaultResponseContentFactory, ResponseContentMatcher, ResponseContentMatcherProvider } from './response-content-matcher';
|
|
55
54
|
import { ChatHistoryEntry } from './chat-history-entry';
|
|
55
|
+
import { ChatToolRequestService } from './chat-tool-request-service';
|
|
56
56
|
|
|
57
57
|
/**
|
|
58
58
|
* A conversation consists of a sequence of ChatMessages.
|
|
@@ -123,10 +123,12 @@ export abstract class AbstractChatAgent {
|
|
|
123
123
|
@inject(LanguageModelRegistry) protected languageModelRegistry: LanguageModelRegistry;
|
|
124
124
|
@inject(ILogger) protected logger: ILogger;
|
|
125
125
|
@inject(CommunicationRecordingService) protected recordingService: CommunicationRecordingService;
|
|
126
|
+
@inject(ChatToolRequestService) protected chatToolRequestService: ChatToolRequestService;
|
|
126
127
|
@inject(PromptService) protected promptService: PromptService;
|
|
127
128
|
|
|
128
129
|
@inject(ContributionProvider) @named(ResponseContentMatcherProvider)
|
|
129
130
|
protected contentMatcherProviders: ContributionProvider<ResponseContentMatcherProvider>;
|
|
131
|
+
protected additionalToolRequests: ToolRequest[] = [];
|
|
130
132
|
protected contentMatchers: ResponseContentMatcher[] = [];
|
|
131
133
|
|
|
132
134
|
@inject(DefaultResponseContentFactory)
|
|
@@ -171,7 +173,6 @@ export abstract class AbstractChatAgent {
|
|
|
171
173
|
);
|
|
172
174
|
}
|
|
173
175
|
|
|
174
|
-
const tools: Map<string, ToolRequest> = new Map();
|
|
175
176
|
if (systemMessageDescription) {
|
|
176
177
|
const systemMsg: ChatMessage = {
|
|
177
178
|
actor: 'system',
|
|
@@ -180,24 +181,20 @@ export abstract class AbstractChatAgent {
|
|
|
180
181
|
};
|
|
181
182
|
// insert system message at the beginning of the request messages
|
|
182
183
|
messages.unshift(systemMsg);
|
|
183
|
-
systemMessageDescription.functionDescriptions?.forEach((tool, id) => {
|
|
184
|
-
tools.set(id, tool);
|
|
185
|
-
});
|
|
186
184
|
}
|
|
187
|
-
this.getTools(request)?.forEach(tool => tools.set(tool.id, tool));
|
|
188
185
|
|
|
189
|
-
const
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
186
|
+
const systemMessageToolRequests = systemMessageDescription?.functionDescriptions?.values();
|
|
187
|
+
const tools = [
|
|
188
|
+
...this.chatToolRequestService.getChatToolRequests(request),
|
|
189
|
+
...this.chatToolRequestService.toChatToolRequests(systemMessageToolRequests ? Array.from(systemMessageToolRequests) : [], request),
|
|
190
|
+
...this.chatToolRequestService.toChatToolRequests(this.additionalToolRequests, request)
|
|
191
|
+
];
|
|
195
192
|
|
|
196
193
|
const languageModelResponse = await this.callLlm(
|
|
197
194
|
languageModel,
|
|
198
195
|
messages,
|
|
199
|
-
tools.
|
|
200
|
-
cancellationToken
|
|
196
|
+
tools.length > 0 ? tools : undefined,
|
|
197
|
+
request.response.cancellationToken
|
|
201
198
|
);
|
|
202
199
|
await this.addContentsToResponse(languageModelResponse, request);
|
|
203
200
|
await this.onResponseComplete(request);
|
|
@@ -265,15 +262,6 @@ export abstract class AbstractChatAgent {
|
|
|
265
262
|
return requestMessages;
|
|
266
263
|
}
|
|
267
264
|
|
|
268
|
-
/**
|
|
269
|
-
* @returns the list of tools used by this agent, or undefined if none is needed.
|
|
270
|
-
*/
|
|
271
|
-
protected getTools(request: ChatRequestModel): ToolRequest[] | undefined {
|
|
272
|
-
return request.message.toolRequests.size > 0
|
|
273
|
-
? [...request.message.toolRequests.values()]
|
|
274
|
-
: undefined;
|
|
275
|
-
}
|
|
276
|
-
|
|
277
265
|
protected async callLlm(
|
|
278
266
|
languageModel: LanguageModel,
|
|
279
267
|
messages: ChatMessage[],
|
package/src/common/chat-model.ts
CHANGED
|
@@ -19,11 +19,12 @@
|
|
|
19
19
|
*--------------------------------------------------------------------------------------------*/
|
|
20
20
|
// Partially copied from https://github.com/microsoft/vscode/blob/a2cab7255c0df424027be05d58e1b7b941f4ea60/src/vs/workbench/contrib/chat/common/chatModel.ts
|
|
21
21
|
|
|
22
|
-
import { Command, Emitter, Event, generateUuid, URI } from '@theia/core';
|
|
22
|
+
import { CancellationToken, CancellationTokenSource, Command, Disposable, Emitter, Event, generateUuid, URI } from '@theia/core';
|
|
23
23
|
import { MarkdownString, MarkdownStringImpl } from '@theia/core/lib/common/markdown-rendering';
|
|
24
24
|
import { Position } from '@theia/core/shared/vscode-languageserver-protocol';
|
|
25
25
|
import { ChatAgentLocation } from './chat-agents';
|
|
26
|
-
import { ParsedChatRequest } from './parsed-chat-request';
|
|
26
|
+
import { ParsedChatRequest, ParsedChatRequestVariablePart } from './parsed-chat-request';
|
|
27
|
+
import { ResolvedAIVariable } from '@theia/ai-core';
|
|
27
28
|
|
|
28
29
|
/**********************
|
|
29
30
|
* INTERFACES AND TYPE GUARDS
|
|
@@ -32,7 +33,11 @@ import { ParsedChatRequest } from './parsed-chat-request';
|
|
|
32
33
|
export type ChatChangeEvent =
|
|
33
34
|
| ChatAddRequestEvent
|
|
34
35
|
| ChatAddResponseEvent
|
|
35
|
-
| ChatRemoveRequestEvent
|
|
36
|
+
| ChatRemoveRequestEvent
|
|
37
|
+
| ChatSetChangeSetEvent
|
|
38
|
+
| ChatSetChangeDeleteEvent
|
|
39
|
+
| ChatUpdateChangeSetEvent
|
|
40
|
+
| ChatRemoveChangeSetEvent;
|
|
36
41
|
|
|
37
42
|
export interface ChatAddRequestEvent {
|
|
38
43
|
kind: 'addRequest';
|
|
@@ -44,6 +49,31 @@ export interface ChatAddResponseEvent {
|
|
|
44
49
|
response: ChatResponseModel;
|
|
45
50
|
}
|
|
46
51
|
|
|
52
|
+
export interface ChatSetChangeSetEvent {
|
|
53
|
+
kind: 'setChangeSet';
|
|
54
|
+
changeSet: ChangeSet;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
export interface ChatSetChangeDeleteEvent {
|
|
58
|
+
kind: 'deleteChangeSet';
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
export interface ChatUpdateChangeSetEvent {
|
|
62
|
+
kind: 'updateChangeSet';
|
|
63
|
+
changeSet: ChangeSet;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
export interface ChatRemoveChangeSetEvent {
|
|
67
|
+
kind: 'removeChangeSet';
|
|
68
|
+
changeSet: ChangeSet;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
export namespace ChatChangeEvent {
|
|
72
|
+
export function isChangeSetEvent(event: ChatChangeEvent): event is ChatSetChangeSetEvent | ChatUpdateChangeSetEvent | ChatRemoveChangeSetEvent {
|
|
73
|
+
return event.kind === 'setChangeSet' || event.kind === 'deleteChangeSet' || event.kind === 'removeChangeSet' || event.kind === 'updateChangeSet';
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
|
|
47
77
|
export type ChatRequestRemovalReason = 'removal' | 'resend' | 'adoption';
|
|
48
78
|
|
|
49
79
|
export interface ChatRemoveRequestEvent {
|
|
@@ -57,10 +87,33 @@ export interface ChatModel {
|
|
|
57
87
|
readonly onDidChange: Event<ChatChangeEvent>;
|
|
58
88
|
readonly id: string;
|
|
59
89
|
readonly location: ChatAgentLocation;
|
|
90
|
+
readonly changeSet?: ChangeSet;
|
|
60
91
|
getRequests(): ChatRequestModel[];
|
|
61
92
|
isEmpty(): boolean;
|
|
62
93
|
}
|
|
63
94
|
|
|
95
|
+
export interface ChangeSet {
|
|
96
|
+
readonly title: string;
|
|
97
|
+
getElements(): ChangeSetElement[];
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
export interface ChangeSetElement {
|
|
101
|
+
readonly uri: URI;
|
|
102
|
+
|
|
103
|
+
readonly name?: string;
|
|
104
|
+
readonly icon?: string;
|
|
105
|
+
readonly additionalInfo?: string;
|
|
106
|
+
|
|
107
|
+
readonly state?: 'pending' | 'applied' | 'discarded';
|
|
108
|
+
readonly type?: 'add' | 'modify' | 'delete';
|
|
109
|
+
readonly data?: { [key: string]: unknown };
|
|
110
|
+
|
|
111
|
+
open?(): Promise<void>;
|
|
112
|
+
openChange?(): Promise<void>;
|
|
113
|
+
accept?(): Promise<void>;
|
|
114
|
+
discard?(): Promise<void>;
|
|
115
|
+
}
|
|
116
|
+
|
|
64
117
|
export interface ChatRequest {
|
|
65
118
|
readonly text: string;
|
|
66
119
|
readonly displayText?: string;
|
|
@@ -76,6 +129,32 @@ export interface ChatRequestModel {
|
|
|
76
129
|
readonly data?: { [key: string]: unknown };
|
|
77
130
|
}
|
|
78
131
|
|
|
132
|
+
export namespace ChatRequestModel {
|
|
133
|
+
export function is(request: unknown): request is ChatRequestModel {
|
|
134
|
+
return !!(
|
|
135
|
+
request &&
|
|
136
|
+
typeof request === 'object' &&
|
|
137
|
+
'id' in request &&
|
|
138
|
+
typeof (request as { id: unknown }).id === 'string' &&
|
|
139
|
+
'session' in request &&
|
|
140
|
+
'request' in request &&
|
|
141
|
+
'response' in request &&
|
|
142
|
+
'message' in request
|
|
143
|
+
);
|
|
144
|
+
}
|
|
145
|
+
export function isInProgress(request: ChatRequestModel | undefined): boolean {
|
|
146
|
+
if (!request) {
|
|
147
|
+
return false;
|
|
148
|
+
}
|
|
149
|
+
const response = request.response;
|
|
150
|
+
return !(
|
|
151
|
+
response.isComplete ||
|
|
152
|
+
response.isCanceled ||
|
|
153
|
+
response.isError
|
|
154
|
+
);
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
|
|
79
158
|
export interface ChatProgressMessage {
|
|
80
159
|
kind: 'progressMessage';
|
|
81
160
|
id: string;
|
|
@@ -386,6 +465,8 @@ export class ChatModelImpl implements ChatModel {
|
|
|
386
465
|
|
|
387
466
|
protected _requests: ChatRequestModelImpl[];
|
|
388
467
|
protected _id: string;
|
|
468
|
+
protected _changeSetListener?: Disposable;
|
|
469
|
+
protected _changeSet?: ChangeSetImpl;
|
|
389
470
|
|
|
390
471
|
constructor(public readonly location = ChatAgentLocation.Panel) {
|
|
391
472
|
// TODO accept serialized data as a parameter to restore a previously saved ChatModel
|
|
@@ -397,12 +478,52 @@ export class ChatModelImpl implements ChatModel {
|
|
|
397
478
|
return this._requests;
|
|
398
479
|
}
|
|
399
480
|
|
|
481
|
+
getRequest(id: string): ChatRequestModelImpl | undefined {
|
|
482
|
+
return this._requests.find(request => request.id === id);
|
|
483
|
+
}
|
|
484
|
+
|
|
400
485
|
get id(): string {
|
|
401
486
|
return this._id;
|
|
402
487
|
}
|
|
403
488
|
|
|
404
|
-
|
|
405
|
-
|
|
489
|
+
get changeSet(): ChangeSetImpl | undefined {
|
|
490
|
+
return this._changeSet;
|
|
491
|
+
}
|
|
492
|
+
|
|
493
|
+
setChangeSet(changeSet: ChangeSetImpl | undefined): void {
|
|
494
|
+
this._changeSet = changeSet;
|
|
495
|
+
if (this._changeSet === undefined) {
|
|
496
|
+
this._changeSetListener?.dispose();
|
|
497
|
+
this._onDidChangeEmitter.fire({
|
|
498
|
+
kind: 'deleteChangeSet',
|
|
499
|
+
});
|
|
500
|
+
return;
|
|
501
|
+
}
|
|
502
|
+
this._onDidChangeEmitter.fire({
|
|
503
|
+
kind: 'setChangeSet',
|
|
504
|
+
changeSet: this._changeSet,
|
|
505
|
+
});
|
|
506
|
+
this._changeSetListener = this._changeSet.onDidChange(() => {
|
|
507
|
+
this._onDidChangeEmitter.fire({
|
|
508
|
+
kind: 'updateChangeSet',
|
|
509
|
+
changeSet: this._changeSet!,
|
|
510
|
+
});
|
|
511
|
+
});
|
|
512
|
+
}
|
|
513
|
+
|
|
514
|
+
removeChangeSet(): void {
|
|
515
|
+
if (this._changeSet) {
|
|
516
|
+
const oldChangeSet = this._changeSet;
|
|
517
|
+
this._changeSet = undefined;
|
|
518
|
+
this._onDidChangeEmitter.fire({
|
|
519
|
+
kind: 'removeChangeSet',
|
|
520
|
+
changeSet: oldChangeSet,
|
|
521
|
+
});
|
|
522
|
+
}
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
addRequest(parsedChatRequest: ParsedChatRequest, agentId?: string, context: ResolvedAIVariable[] = []): ChatRequestModelImpl {
|
|
526
|
+
const requestModel = new ChatRequestModelImpl(this, parsedChatRequest, agentId, context);
|
|
406
527
|
this._requests.push(requestModel);
|
|
407
528
|
this._onDidChangeEmitter.fire({
|
|
408
529
|
kind: 'addRequest',
|
|
@@ -416,21 +537,72 @@ export class ChatModelImpl implements ChatModel {
|
|
|
416
537
|
}
|
|
417
538
|
}
|
|
418
539
|
|
|
540
|
+
export class ChangeSetImpl implements ChangeSet {
|
|
541
|
+
protected readonly _onDidChangeEmitter = new Emitter<void>();
|
|
542
|
+
onDidChange: Event<void> = this._onDidChangeEmitter.event;
|
|
543
|
+
|
|
544
|
+
protected _elements: ChangeSetElement[] = [];
|
|
545
|
+
|
|
546
|
+
constructor(public readonly title: string, elements: ChangeSetElement[] = []) {
|
|
547
|
+
this.addElements(elements);
|
|
548
|
+
}
|
|
549
|
+
|
|
550
|
+
getElements(): ChangeSetElement[] {
|
|
551
|
+
return this._elements;
|
|
552
|
+
}
|
|
553
|
+
|
|
554
|
+
addElement(element: ChangeSetElement): void {
|
|
555
|
+
this.addElements([element]);
|
|
556
|
+
}
|
|
557
|
+
|
|
558
|
+
addElements(elements: ChangeSetElement[]): void {
|
|
559
|
+
this._elements.push(...elements);
|
|
560
|
+
this.notifyChange();
|
|
561
|
+
}
|
|
562
|
+
|
|
563
|
+
replaceElement(element: ChangeSetElement): boolean {
|
|
564
|
+
const index = this._elements.findIndex(e => e.uri.toString() === element.uri.toString());
|
|
565
|
+
if (index < 0) {
|
|
566
|
+
return false;
|
|
567
|
+
}
|
|
568
|
+
this._elements[index] = element;
|
|
569
|
+
this.notifyChange();
|
|
570
|
+
return true;
|
|
571
|
+
}
|
|
572
|
+
|
|
573
|
+
addOrReplaceElement(element: ChangeSetElement): void {
|
|
574
|
+
if (!this.replaceElement(element)) {
|
|
575
|
+
this.addElement(element);
|
|
576
|
+
}
|
|
577
|
+
}
|
|
578
|
+
|
|
579
|
+
removeElement(index: number): void {
|
|
580
|
+
this._elements.splice(index, 1);
|
|
581
|
+
this.notifyChange();
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
notifyChange(): void {
|
|
585
|
+
this._onDidChangeEmitter.fire();
|
|
586
|
+
}
|
|
587
|
+
}
|
|
588
|
+
|
|
419
589
|
export class ChatRequestModelImpl implements ChatRequestModel {
|
|
420
590
|
protected readonly _id: string;
|
|
421
|
-
protected _session:
|
|
591
|
+
protected _session: ChatModelImpl;
|
|
422
592
|
protected _request: ChatRequest;
|
|
423
593
|
protected _response: ChatResponseModelImpl;
|
|
594
|
+
protected _context: ResolvedAIVariable[];
|
|
424
595
|
protected _agentId?: string;
|
|
425
596
|
protected _data: { [key: string]: unknown };
|
|
426
597
|
|
|
427
|
-
constructor(session:
|
|
428
|
-
data: { [key: string]: unknown } = {}) {
|
|
598
|
+
constructor(session: ChatModelImpl, public readonly message: ParsedChatRequest, agentId?: string,
|
|
599
|
+
context: ResolvedAIVariable[] = [], data: { [key: string]: unknown } = {}) {
|
|
429
600
|
// TODO accept serialized data as a parameter to restore a previously saved ChatRequestModel
|
|
430
601
|
this._request = message.request;
|
|
431
602
|
this._id = generateUuid();
|
|
432
603
|
this._session = session;
|
|
433
604
|
this._response = new ChatResponseModelImpl(this._id, agentId);
|
|
605
|
+
this._context = context.concat(message.parts.filter(part => part.kind === 'var').map(part => (part as ParsedChatRequestVariablePart).resolution));
|
|
434
606
|
this._agentId = agentId;
|
|
435
607
|
this._data = data;
|
|
436
608
|
}
|
|
@@ -451,7 +623,7 @@ export class ChatRequestModelImpl implements ChatRequestModel {
|
|
|
451
623
|
return this._id;
|
|
452
624
|
}
|
|
453
625
|
|
|
454
|
-
get session():
|
|
626
|
+
get session(): ChatModelImpl {
|
|
455
627
|
return this._session;
|
|
456
628
|
}
|
|
457
629
|
|
|
@@ -466,6 +638,10 @@ export class ChatRequestModelImpl implements ChatRequestModel {
|
|
|
466
638
|
get agentId(): string | undefined {
|
|
467
639
|
return this._agentId;
|
|
468
640
|
}
|
|
641
|
+
|
|
642
|
+
cancel(): void {
|
|
643
|
+
this.response.cancel();
|
|
644
|
+
}
|
|
469
645
|
}
|
|
470
646
|
|
|
471
647
|
export class ErrorChatResponseContentImpl implements ErrorChatResponseContent {
|
|
@@ -798,11 +974,11 @@ class ChatResponseModelImpl implements ChatResponseModel {
|
|
|
798
974
|
protected _progressMessages: ChatProgressMessage[];
|
|
799
975
|
protected _response: ChatResponseImpl;
|
|
800
976
|
protected _isComplete: boolean;
|
|
801
|
-
protected _isCanceled: boolean;
|
|
802
977
|
protected _isWaitingForInput: boolean;
|
|
803
978
|
protected _agentId?: string;
|
|
804
979
|
protected _isError: boolean;
|
|
805
980
|
protected _errorObject: Error | undefined;
|
|
981
|
+
protected _cancellationToken: CancellationTokenSource;
|
|
806
982
|
|
|
807
983
|
constructor(requestId: string, agentId?: string) {
|
|
808
984
|
// TODO accept serialized data as a parameter to restore a previously saved ChatResponseModel
|
|
@@ -813,9 +989,9 @@ class ChatResponseModelImpl implements ChatResponseModel {
|
|
|
813
989
|
response.onDidChange(() => this._onDidChangeEmitter.fire());
|
|
814
990
|
this._response = response;
|
|
815
991
|
this._isComplete = false;
|
|
816
|
-
this._isCanceled = false;
|
|
817
992
|
this._isWaitingForInput = false;
|
|
818
993
|
this._agentId = agentId;
|
|
994
|
+
this._cancellationToken = new CancellationTokenSource();
|
|
819
995
|
}
|
|
820
996
|
|
|
821
997
|
get id(): string {
|
|
@@ -870,7 +1046,7 @@ class ChatResponseModelImpl implements ChatResponseModel {
|
|
|
870
1046
|
}
|
|
871
1047
|
|
|
872
1048
|
get isCanceled(): boolean {
|
|
873
|
-
return this.
|
|
1049
|
+
return this._cancellationToken.token.isCancellationRequested;
|
|
874
1050
|
}
|
|
875
1051
|
|
|
876
1052
|
get isWaitingForInput(): boolean {
|
|
@@ -892,12 +1068,16 @@ class ChatResponseModelImpl implements ChatResponseModel {
|
|
|
892
1068
|
}
|
|
893
1069
|
|
|
894
1070
|
cancel(): void {
|
|
1071
|
+
this._cancellationToken.cancel();
|
|
895
1072
|
this._isComplete = true;
|
|
896
|
-
this._isCanceled = true;
|
|
897
1073
|
this._isWaitingForInput = false;
|
|
898
1074
|
this._onDidChangeEmitter.fire();
|
|
899
1075
|
}
|
|
900
1076
|
|
|
1077
|
+
get cancellationToken(): CancellationToken {
|
|
1078
|
+
return this._cancellationToken.token;
|
|
1079
|
+
}
|
|
1080
|
+
|
|
901
1081
|
waitForInput(): void {
|
|
902
1082
|
this._isWaitingForInput = true;
|
|
903
1083
|
this._onDidChangeEmitter.fire();
|
|
@@ -910,7 +1090,6 @@ class ChatResponseModelImpl implements ChatResponseModel {
|
|
|
910
1090
|
|
|
911
1091
|
error(error: Error): void {
|
|
912
1092
|
this._isComplete = true;
|
|
913
|
-
this._isCanceled = false;
|
|
914
1093
|
this._isWaitingForInput = false;
|
|
915
1094
|
this._isError = true;
|
|
916
1095
|
this._errorObject = error;
|
|
@@ -86,6 +86,11 @@ export interface ChatService {
|
|
|
86
86
|
sessionId: string,
|
|
87
87
|
request: ChatRequest
|
|
88
88
|
): Promise<ChatRequestInvocation | undefined>;
|
|
89
|
+
|
|
90
|
+
deleteChangeSet(sessionId: string): void;
|
|
91
|
+
deleteChangeSetElement(sessionId: string, index: number): void;
|
|
92
|
+
|
|
93
|
+
cancelRequest(sessionId: string, requestId: string): Promise<void>;
|
|
89
94
|
}
|
|
90
95
|
|
|
91
96
|
interface ChatSessionInternal extends ChatSession {
|
|
@@ -219,6 +224,10 @@ export class ChatServiceImpl implements ChatService {
|
|
|
219
224
|
return invocation;
|
|
220
225
|
}
|
|
221
226
|
|
|
227
|
+
async cancelRequest(sessionId: string, requestId: string): Promise<void> {
|
|
228
|
+
return this.getSession(sessionId)?.model.getRequest(requestId)?.response.cancel();
|
|
229
|
+
}
|
|
230
|
+
|
|
222
231
|
protected getAgent(parsedRequest: ParsedChatRequest): ChatAgent | undefined {
|
|
223
232
|
const agentPart = this.getMentionedAgent(parsedRequest);
|
|
224
233
|
if (agentPart) {
|
|
@@ -233,4 +242,12 @@ export class ChatServiceImpl implements ChatService {
|
|
|
233
242
|
protected getMentionedAgent(parsedRequest: ParsedChatRequest): ParsedChatRequestAgentPart | undefined {
|
|
234
243
|
return parsedRequest.parts.find(p => p instanceof ParsedChatRequestAgentPart) as ParsedChatRequestAgentPart | undefined;
|
|
235
244
|
}
|
|
245
|
+
|
|
246
|
+
deleteChangeSet(sessionId: string): void {
|
|
247
|
+
this.getSession(sessionId)?.model.setChangeSet(undefined);
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
deleteChangeSetElement(sessionId: string, index: number): void {
|
|
251
|
+
this.getSession(sessionId)?.model.changeSet?.removeElement(index);
|
|
252
|
+
}
|
|
236
253
|
}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
// *****************************************************************************
|
|
2
|
+
// Copyright (C) 2025 EclipseSource GmbH.
|
|
3
|
+
//
|
|
4
|
+
// This program and the accompanying materials are made available under the
|
|
5
|
+
// terms of the Eclipse Public License v. 2.0 which is available at
|
|
6
|
+
// http://www.eclipse.org/legal/epl-2.0.
|
|
7
|
+
//
|
|
8
|
+
// This Source Code may also be made available under the following Secondary
|
|
9
|
+
// Licenses when the conditions for such availability set forth in the Eclipse
|
|
10
|
+
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
|
11
|
+
// with the GNU Classpath Exception which is available at
|
|
12
|
+
// https://www.gnu.org/software/classpath/license.html.
|
|
13
|
+
//
|
|
14
|
+
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
|
15
|
+
// *****************************************************************************
|
|
16
|
+
|
|
17
|
+
import { ToolRequest } from '@theia/ai-core';
|
|
18
|
+
import { injectable } from '@theia/core/shared/inversify';
|
|
19
|
+
import { ChatRequestModelImpl } from './chat-model';
|
|
20
|
+
|
|
21
|
+
export interface ChatToolRequest extends ToolRequest {
|
|
22
|
+
handler: (
|
|
23
|
+
arg_string: string,
|
|
24
|
+
context: ChatRequestModelImpl,
|
|
25
|
+
) => Promise<unknown>;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* Wraps tool requests in a chat context.
|
|
30
|
+
*
|
|
31
|
+
* This service extracts tool requests from a given chat request model and wraps their
|
|
32
|
+
* handler functions to provide additional context, such as the chat request model.
|
|
33
|
+
*/
|
|
34
|
+
@injectable()
|
|
35
|
+
export class ChatToolRequestService {
|
|
36
|
+
|
|
37
|
+
getChatToolRequests(request: ChatRequestModelImpl): ChatToolRequest[] {
|
|
38
|
+
const toolRequests = request.message.toolRequests.size > 0 ? [...request.message.toolRequests.values()] : undefined;
|
|
39
|
+
if (!toolRequests) {
|
|
40
|
+
return [];
|
|
41
|
+
}
|
|
42
|
+
return this.toChatToolRequests(toolRequests, request);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
toChatToolRequests(toolRequests: ToolRequest[] | undefined, request: ChatRequestModelImpl): ChatToolRequest[] {
|
|
46
|
+
if (!toolRequests) {
|
|
47
|
+
return [];
|
|
48
|
+
}
|
|
49
|
+
return toolRequests.map(toolRequest => this.toChatToolRequest(toolRequest, request));
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
protected toChatToolRequest(toolRequest: ToolRequest, request: ChatRequestModelImpl): ChatToolRequest {
|
|
53
|
+
return {
|
|
54
|
+
...toolRequest,
|
|
55
|
+
handler: async (arg_string: string) => toolRequest.handler(arg_string, request)
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
}
|
|
@@ -315,7 +315,7 @@ export class CommandChatAgent extends AbstractTextToModelParsingChatAgent<Parsed
|
|
|
315
315
|
const theiaCommand = this.commandRegistry.getCommand(parsedCommand.commandId);
|
|
316
316
|
if (theiaCommand === undefined) {
|
|
317
317
|
console.error(`No Theia Command with id ${parsedCommand.commandId}`);
|
|
318
|
-
request.
|
|
318
|
+
request.cancel();
|
|
319
319
|
}
|
|
320
320
|
const args = parsedCommand.arguments !== undefined &&
|
|
321
321
|
parsedCommand.arguments.length > 0
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { ChatAgent, AbstractStreamParsingChatAgent, SystemMessageDescription } from './chat-agents';
|
|
2
|
-
import { AgentSpecificVariables, PromptTemplate } from '@theia/ai-core';
|
|
3
|
-
export declare class O1ChatAgent extends AbstractStreamParsingChatAgent implements ChatAgent {
|
|
4
|
-
name: string;
|
|
5
|
-
description: string;
|
|
6
|
-
promptTemplates: PromptTemplate[];
|
|
7
|
-
readonly agentSpecificVariables: AgentSpecificVariables[];
|
|
8
|
-
readonly variables: string[];
|
|
9
|
-
readonly functions: string[];
|
|
10
|
-
constructor();
|
|
11
|
-
protected getSystemMessageDescription(): Promise<SystemMessageDescription | undefined>;
|
|
12
|
-
}
|
|
13
|
-
//# sourceMappingURL=o1-chat-agent.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"o1-chat-agent.d.ts","sourceRoot":"","sources":["../../src/common/o1-chat-agent.ts"],"names":[],"mappings":"AAgBA,OAAO,EACH,SAAS,EACT,8BAA8B,EAC9B,wBAAwB,EAC3B,MAAM,eAAe,CAAC;AAGvB,OAAO,EAAE,sBAAsB,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC;AAExE,qBACa,WAAY,SAAQ,8BAA+B,YAAW,SAAS;IAEzE,IAAI,SAAgB;IACpB,WAAW,SAAsD;IACjE,eAAe,EAAE,cAAc,EAAE,CAAM;IAC9C,QAAQ,CAAC,sBAAsB,EAAE,sBAAsB,EAAE,CAAM;IAC/D,QAAQ,CAAC,SAAS,EAAE,MAAM,EAAE,CAAM;IAClC,QAAQ,CAAC,SAAS,EAAE,MAAM,EAAE,CAAM;;cAalB,2BAA2B,IAAI,OAAO,CAAC,wBAAwB,GAAG,SAAS,CAAC;CAI/F"}
|
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
// *****************************************************************************
|
|
3
|
-
// Copyright (C) 2024 EclipseSource GmbH.
|
|
4
|
-
//
|
|
5
|
-
// This program and the accompanying materials are made available under the
|
|
6
|
-
// terms of the Eclipse Public License v. 2.0 which is available at
|
|
7
|
-
// http://www.eclipse.org/legal/epl-2.0.
|
|
8
|
-
//
|
|
9
|
-
// This Source Code may also be made available under the following Secondary
|
|
10
|
-
// Licenses when the conditions for such availability set forth in the Eclipse
|
|
11
|
-
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
|
12
|
-
// with the GNU Classpath Exception which is available at
|
|
13
|
-
// https://www.gnu.org/software/classpath/license.html.
|
|
14
|
-
//
|
|
15
|
-
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
|
16
|
-
// *****************************************************************************
|
|
17
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
18
|
-
exports.O1ChatAgent = void 0;
|
|
19
|
-
const tslib_1 = require("tslib");
|
|
20
|
-
const chat_agents_1 = require("./chat-agents");
|
|
21
|
-
const inversify_1 = require("@theia/core/shared/inversify");
|
|
22
|
-
let O1ChatAgent = class O1ChatAgent extends chat_agents_1.AbstractStreamParsingChatAgent {
|
|
23
|
-
constructor() {
|
|
24
|
-
super('o1-preview', [{
|
|
25
|
-
purpose: 'chat',
|
|
26
|
-
identifier: 'openai/o1-preview',
|
|
27
|
-
}], 'chat');
|
|
28
|
-
this.name = 'O1-Preview';
|
|
29
|
-
this.description = 'An agent for interacting with ChatGPT o1-preview';
|
|
30
|
-
this.promptTemplates = [];
|
|
31
|
-
this.agentSpecificVariables = [];
|
|
32
|
-
this.variables = [];
|
|
33
|
-
this.functions = [];
|
|
34
|
-
}
|
|
35
|
-
async getSystemMessageDescription() {
|
|
36
|
-
// O1 currently does not support system prompts
|
|
37
|
-
return undefined;
|
|
38
|
-
}
|
|
39
|
-
};
|
|
40
|
-
exports.O1ChatAgent = O1ChatAgent;
|
|
41
|
-
exports.O1ChatAgent = O1ChatAgent = tslib_1.__decorate([
|
|
42
|
-
(0, inversify_1.injectable)(),
|
|
43
|
-
tslib_1.__metadata("design:paramtypes", [])
|
|
44
|
-
], O1ChatAgent);
|
|
45
|
-
//# sourceMappingURL=o1-chat-agent.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"o1-chat-agent.js","sourceRoot":"","sources":["../../src/common/o1-chat-agent.ts"],"names":[],"mappings":";AAAA,gFAAgF;AAChF,yCAAyC;AACzC,EAAE;AACF,2EAA2E;AAC3E,mEAAmE;AACnE,wCAAwC;AACxC,EAAE;AACF,4EAA4E;AAC5E,8EAA8E;AAC9E,6EAA6E;AAC7E,yDAAyD;AACzD,uDAAuD;AACvD,EAAE;AACF,gFAAgF;AAChF,gFAAgF;;;;AAEhF,+CAIuB;AAEvB,4DAA0D;AAInD,IAAM,WAAW,GAAjB,MAAM,WAAY,SAAQ,4CAA8B;IAS3D;QACI,KAAK,CACD,YAAY,EACZ,CAAC;gBACG,OAAO,EAAE,MAAM;gBACf,UAAU,EAAE,mBAAmB;aAClC,CAAC,EACF,MAAM,CACT,CAAC;QAfC,SAAI,GAAG,YAAY,CAAC;QACpB,gBAAW,GAAG,kDAAkD,CAAC;QACjE,oBAAe,GAAqB,EAAE,CAAC;QACrC,2BAAsB,GAA6B,EAAE,CAAC;QACtD,cAAS,GAAa,EAAE,CAAC;QACzB,cAAS,GAAa,EAAE,CAAC;IAWlC,CAAC;IAES,KAAK,CAAC,2BAA2B;QACvC,+CAA+C;QAC/C,OAAO,SAAS,CAAC;IACrB,CAAC;CACJ,CAAA;AAxBY,kCAAW;sBAAX,WAAW;IADvB,IAAA,sBAAU,GAAE;;GACA,WAAW,CAwBvB"}
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
// *****************************************************************************
|
|
2
|
-
// Copyright (C) 2024 EclipseSource GmbH.
|
|
3
|
-
//
|
|
4
|
-
// This program and the accompanying materials are made available under the
|
|
5
|
-
// terms of the Eclipse Public License v. 2.0 which is available at
|
|
6
|
-
// http://www.eclipse.org/legal/epl-2.0.
|
|
7
|
-
//
|
|
8
|
-
// This Source Code may also be made available under the following Secondary
|
|
9
|
-
// Licenses when the conditions for such availability set forth in the Eclipse
|
|
10
|
-
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
|
11
|
-
// with the GNU Classpath Exception which is available at
|
|
12
|
-
// https://www.gnu.org/software/classpath/license.html.
|
|
13
|
-
//
|
|
14
|
-
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
|
15
|
-
// *****************************************************************************
|
|
16
|
-
|
|
17
|
-
import {
|
|
18
|
-
ChatAgent,
|
|
19
|
-
AbstractStreamParsingChatAgent,
|
|
20
|
-
SystemMessageDescription
|
|
21
|
-
} from './chat-agents';
|
|
22
|
-
|
|
23
|
-
import { injectable } from '@theia/core/shared/inversify';
|
|
24
|
-
import { AgentSpecificVariables, PromptTemplate } from '@theia/ai-core';
|
|
25
|
-
|
|
26
|
-
@injectable()
|
|
27
|
-
export class O1ChatAgent extends AbstractStreamParsingChatAgent implements ChatAgent {
|
|
28
|
-
|
|
29
|
-
public name = 'O1-Preview';
|
|
30
|
-
public description = 'An agent for interacting with ChatGPT o1-preview';
|
|
31
|
-
public promptTemplates: PromptTemplate[] = [];
|
|
32
|
-
readonly agentSpecificVariables: AgentSpecificVariables[] = [];
|
|
33
|
-
readonly variables: string[] = [];
|
|
34
|
-
readonly functions: string[] = [];
|
|
35
|
-
|
|
36
|
-
constructor() {
|
|
37
|
-
super(
|
|
38
|
-
'o1-preview',
|
|
39
|
-
[{
|
|
40
|
-
purpose: 'chat',
|
|
41
|
-
identifier: 'openai/o1-preview',
|
|
42
|
-
}],
|
|
43
|
-
'chat'
|
|
44
|
-
);
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
protected async getSystemMessageDescription(): Promise<SystemMessageDescription | undefined> {
|
|
48
|
-
// O1 currently does not support system prompts
|
|
49
|
-
return undefined;
|
|
50
|
-
}
|
|
51
|
-
}
|