jupyterlab-chat 0.11.0 → 0.12.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/factory.d.ts +3 -0
- package/lib/factory.js +2 -0
- package/lib/model.d.ts +10 -3
- package/lib/model.js +25 -6
- package/lib/token.d.ts +6 -0
- package/lib/token.js +6 -0
- package/lib/widget.d.ts +2 -0
- package/lib/widget.js +3 -1
- package/package.json +2 -2
- package/src/factory.ts +5 -0
- package/src/model.ts +31 -7
- package/src/token.ts +9 -0
- package/src/widget.tsx +5 -1
package/lib/factory.d.ts
CHANGED
|
@@ -54,6 +54,7 @@ export declare class ChatWidgetFactory extends ABCWidgetFactory<LabChatPanel, La
|
|
|
54
54
|
private _attachmentOpenerRegistry?;
|
|
55
55
|
private _inputToolbarFactory?;
|
|
56
56
|
private _messageFooterRegistry?;
|
|
57
|
+
private _welcomeMessage?;
|
|
57
58
|
}
|
|
58
59
|
export declare namespace ChatWidgetFactory {
|
|
59
60
|
interface IContext extends DocumentRegistry.IContext<LabChatModel> {
|
|
@@ -64,6 +65,7 @@ export declare namespace ChatWidgetFactory {
|
|
|
64
65
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
65
66
|
inputToolbarRegistry?: IInputToolbarRegistry;
|
|
66
67
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
68
|
+
welcomeMessage?: string;
|
|
67
69
|
}
|
|
68
70
|
interface IOptions<T extends LabChatPanel> extends DocumentRegistry.IWidgetFactoryOptions<T> {
|
|
69
71
|
themeManager: IThemeManager | null;
|
|
@@ -72,6 +74,7 @@ export declare namespace ChatWidgetFactory {
|
|
|
72
74
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
73
75
|
inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
74
76
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
77
|
+
welcomeMessage?: string;
|
|
75
78
|
}
|
|
76
79
|
}
|
|
77
80
|
export declare class LabChatModelFactory implements DocumentRegistry.IModelFactory<LabChatModel> {
|
package/lib/factory.js
CHANGED
|
@@ -54,6 +54,7 @@ export class ChatWidgetFactory extends ABCWidgetFactory {
|
|
|
54
54
|
this._attachmentOpenerRegistry = options.attachmentOpenerRegistry;
|
|
55
55
|
this._inputToolbarFactory = options.inputToolbarFactory;
|
|
56
56
|
this._messageFooterRegistry = options.messageFooterRegistry;
|
|
57
|
+
this._welcomeMessage = options.welcomeMessage;
|
|
57
58
|
}
|
|
58
59
|
/**
|
|
59
60
|
* Create a new widget given a context.
|
|
@@ -67,6 +68,7 @@ export class ChatWidgetFactory extends ABCWidgetFactory {
|
|
|
67
68
|
context.chatCommandRegistry = this._chatCommandRegistry;
|
|
68
69
|
context.attachmentOpenerRegistry = this._attachmentOpenerRegistry;
|
|
69
70
|
context.messageFooterRegistry = this._messageFooterRegistry;
|
|
71
|
+
context.welcomeMessage = this._welcomeMessage;
|
|
70
72
|
if (this._inputToolbarFactory) {
|
|
71
73
|
context.inputToolbarRegistry = this._inputToolbarFactory.create();
|
|
72
74
|
}
|
package/lib/model.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { AbstractChatModel, AbstractChatContext, IChatContext, IChatMessage, IChatModel,
|
|
1
|
+
import { AbstractChatModel, AbstractChatContext, IChatContext, IChatMessage, IChatModel, INewMessage, IUser } from '@jupyter/chat';
|
|
2
2
|
import { IChangedArgs } from '@jupyterlab/coreutils';
|
|
3
3
|
import { DocumentRegistry } from '@jupyterlab/docregistry';
|
|
4
4
|
import { User } from '@jupyterlab/services';
|
|
@@ -48,9 +48,16 @@ export declare class LabChatModel extends AbstractChatModel implements DocumentR
|
|
|
48
48
|
updateMessage(id: string, updatedMessage: IChatMessage): Promise<boolean | void> | boolean | void;
|
|
49
49
|
deleteMessage(id: string): Promise<boolean | void> | boolean | void;
|
|
50
50
|
/**
|
|
51
|
-
* Function called
|
|
51
|
+
* Function called when the input content changed.
|
|
52
|
+
*
|
|
53
|
+
* @param value - The whole input content.
|
|
54
|
+
* @param messageID - The ID of the message being edited, if any.
|
|
52
55
|
*/
|
|
53
|
-
onInputChanged: (
|
|
56
|
+
onInputChanged: (value: string, messageID?: string) => void;
|
|
57
|
+
/**
|
|
58
|
+
* Listen to the message edition input.
|
|
59
|
+
*/
|
|
60
|
+
onMessageEditionAdded: (_: IChatModel, edition: IChatModel.IMessageEdition) => void;
|
|
54
61
|
/**
|
|
55
62
|
* Triggered when an awareness state changes.
|
|
56
63
|
* Used to populate the writers list.
|
package/lib/model.js
CHANGED
|
@@ -15,9 +15,12 @@ export class LabChatModel extends AbstractChatModel {
|
|
|
15
15
|
super(options);
|
|
16
16
|
this.collaborative = true;
|
|
17
17
|
/**
|
|
18
|
-
* Function called
|
|
18
|
+
* Function called when the input content changed.
|
|
19
|
+
*
|
|
20
|
+
* @param value - The whole input content.
|
|
21
|
+
* @param messageID - The ID of the message being edited, if any.
|
|
19
22
|
*/
|
|
20
|
-
this.onInputChanged = (
|
|
23
|
+
this.onInputChanged = (value, messageID) => {
|
|
21
24
|
if (!value || !this.config.sendTypingNotification) {
|
|
22
25
|
return;
|
|
23
26
|
}
|
|
@@ -25,11 +28,22 @@ export class LabChatModel extends AbstractChatModel {
|
|
|
25
28
|
if (this._timeoutWriting !== null) {
|
|
26
29
|
window.clearTimeout(this._timeoutWriting);
|
|
27
30
|
}
|
|
28
|
-
awareness.setLocalStateField('isWriting', true);
|
|
31
|
+
awareness.setLocalStateField('isWriting', messageID !== null && messageID !== void 0 ? messageID : true);
|
|
29
32
|
this._timeoutWriting = window.setTimeout(() => {
|
|
30
33
|
this._resetWritingStatus();
|
|
31
34
|
}, WRITING_DELAY);
|
|
32
35
|
};
|
|
36
|
+
/**
|
|
37
|
+
* Listen to the message edition input.
|
|
38
|
+
*/
|
|
39
|
+
this.onMessageEditionAdded = (_, edition) => {
|
|
40
|
+
if (edition !== null) {
|
|
41
|
+
const _onInputChanged = (_, value) => {
|
|
42
|
+
this.onInputChanged(value, edition.id);
|
|
43
|
+
};
|
|
44
|
+
edition.model.valueChanged.connect(_onInputChanged);
|
|
45
|
+
}
|
|
46
|
+
};
|
|
33
47
|
/**
|
|
34
48
|
* Triggered when an awareness state changes.
|
|
35
49
|
* Used to populate the writers list.
|
|
@@ -42,8 +56,12 @@ export class LabChatModel extends AbstractChatModel {
|
|
|
42
56
|
if (!state || !state.user || state.user.username === this.user.username) {
|
|
43
57
|
continue;
|
|
44
58
|
}
|
|
45
|
-
if (state.isWriting) {
|
|
46
|
-
|
|
59
|
+
if (state.isWriting !== undefined && state.isWriting !== false) {
|
|
60
|
+
const writer = {
|
|
61
|
+
user: state.user,
|
|
62
|
+
messageID: state.isWriting === true ? undefined : state.isWriting
|
|
63
|
+
};
|
|
64
|
+
writers.push(writer);
|
|
47
65
|
}
|
|
48
66
|
}
|
|
49
67
|
this.updateWriters(writers);
|
|
@@ -136,7 +154,8 @@ export class LabChatModel extends AbstractChatModel {
|
|
|
136
154
|
this.config = config;
|
|
137
155
|
});
|
|
138
156
|
this.sharedModel.awareness.on('change', this.onAwarenessChange);
|
|
139
|
-
this.input.valueChanged.connect(this.onInputChanged);
|
|
157
|
+
this.input.valueChanged.connect((_, value) => this.onInputChanged(value));
|
|
158
|
+
this.messageEditionAdded.connect(this.onMessageEditionAdded);
|
|
140
159
|
}
|
|
141
160
|
get user() {
|
|
142
161
|
return this._user;
|
package/lib/token.d.ts
CHANGED
|
@@ -102,3 +102,9 @@ export interface IInputToolbarRegistryFactory {
|
|
|
102
102
|
* The token of the factory to create an input toolbar registry.
|
|
103
103
|
*/
|
|
104
104
|
export declare const IInputToolbarRegistryFactory: Token<IInputToolbarRegistryFactory>;
|
|
105
|
+
/**
|
|
106
|
+
* The token to add a welcome message to the chat.
|
|
107
|
+
* This token is not provided by default, but can be provided by third party extensions
|
|
108
|
+
* willing to add a welcome message to the chat.
|
|
109
|
+
*/
|
|
110
|
+
export declare const IWelcomeMessage: Token<string>;
|
package/lib/token.js
CHANGED
|
@@ -61,3 +61,9 @@ export const ISelectionWatcherToken = new Token('jupyterlab-chat:ISelectionWatch
|
|
|
61
61
|
* The token of the factory to create an input toolbar registry.
|
|
62
62
|
*/
|
|
63
63
|
export const IInputToolbarRegistryFactory = new Token('jupyterlab-chat:IInputToolbarRegistryFactory');
|
|
64
|
+
/**
|
|
65
|
+
* The token to add a welcome message to the chat.
|
|
66
|
+
* This token is not provided by default, but can be provided by third party extensions
|
|
67
|
+
* willing to add a welcome message to the chat.
|
|
68
|
+
*/
|
|
69
|
+
export const IWelcomeMessage = new Token('jupyterlab-chat:IWelcomeMessage');
|
package/lib/widget.d.ts
CHANGED
|
@@ -92,6 +92,7 @@ export declare class ChatPanel extends SidePanel {
|
|
|
92
92
|
private _attachmentOpenerRegistry?;
|
|
93
93
|
private _inputToolbarFactory?;
|
|
94
94
|
private _messageFooterRegistry?;
|
|
95
|
+
private _welcomeMessage?;
|
|
95
96
|
}
|
|
96
97
|
/**
|
|
97
98
|
* The chat panel namespace.
|
|
@@ -110,6 +111,7 @@ export declare namespace ChatPanel {
|
|
|
110
111
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
111
112
|
inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
112
113
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
114
|
+
welcomeMessage?: string;
|
|
113
115
|
}
|
|
114
116
|
}
|
|
115
117
|
/**
|
package/lib/widget.js
CHANGED
|
@@ -109,6 +109,7 @@ export class ChatPanel extends SidePanel {
|
|
|
109
109
|
this._attachmentOpenerRegistry = options.attachmentOpenerRegistry;
|
|
110
110
|
this._inputToolbarFactory = options.inputToolbarFactory;
|
|
111
111
|
this._messageFooterRegistry = options.messageFooterRegistry;
|
|
112
|
+
this._welcomeMessage = options.welcomeMessage;
|
|
112
113
|
const addChat = new CommandToolbarButton({
|
|
113
114
|
commands: this._commands,
|
|
114
115
|
id: CommandIDs.createChat,
|
|
@@ -166,7 +167,8 @@ export class ChatPanel extends SidePanel {
|
|
|
166
167
|
chatCommandRegistry: this._chatCommandRegistry,
|
|
167
168
|
attachmentOpenerRegistry: this._attachmentOpenerRegistry,
|
|
168
169
|
inputToolbarRegistry,
|
|
169
|
-
messageFooterRegistry: this._messageFooterRegistry
|
|
170
|
+
messageFooterRegistry: this._messageFooterRegistry,
|
|
171
|
+
welcomeMessage: this._welcomeMessage
|
|
170
172
|
});
|
|
171
173
|
this.addWidget(new ChatSection({
|
|
172
174
|
widget,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "jupyterlab-chat",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.12.0",
|
|
4
4
|
"description": "The library to build a chat based on shared document",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"jupyter",
|
|
@@ -42,7 +42,7 @@
|
|
|
42
42
|
"watch:src": "tsc -w --sourceMap"
|
|
43
43
|
},
|
|
44
44
|
"dependencies": {
|
|
45
|
-
"@jupyter/chat": "^0.
|
|
45
|
+
"@jupyter/chat": "^0.12.0",
|
|
46
46
|
"@jupyter/collaborative-drive": "^3.0.0",
|
|
47
47
|
"@jupyter/ydoc": "^2.0.0 || ^3.0.0",
|
|
48
48
|
"@jupyterlab/application": "^4.2.0",
|
package/src/factory.ts
CHANGED
|
@@ -86,6 +86,7 @@ export class ChatWidgetFactory extends ABCWidgetFactory<
|
|
|
86
86
|
this._attachmentOpenerRegistry = options.attachmentOpenerRegistry;
|
|
87
87
|
this._inputToolbarFactory = options.inputToolbarFactory;
|
|
88
88
|
this._messageFooterRegistry = options.messageFooterRegistry;
|
|
89
|
+
this._welcomeMessage = options.welcomeMessage;
|
|
89
90
|
}
|
|
90
91
|
|
|
91
92
|
/**
|
|
@@ -100,6 +101,7 @@ export class ChatWidgetFactory extends ABCWidgetFactory<
|
|
|
100
101
|
context.chatCommandRegistry = this._chatCommandRegistry;
|
|
101
102
|
context.attachmentOpenerRegistry = this._attachmentOpenerRegistry;
|
|
102
103
|
context.messageFooterRegistry = this._messageFooterRegistry;
|
|
104
|
+
context.welcomeMessage = this._welcomeMessage;
|
|
103
105
|
if (this._inputToolbarFactory) {
|
|
104
106
|
context.inputToolbarRegistry = this._inputToolbarFactory.create();
|
|
105
107
|
}
|
|
@@ -115,6 +117,7 @@ export class ChatWidgetFactory extends ABCWidgetFactory<
|
|
|
115
117
|
private _attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
116
118
|
private _inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
117
119
|
private _messageFooterRegistry?: IMessageFooterRegistry;
|
|
120
|
+
private _welcomeMessage?: string;
|
|
118
121
|
}
|
|
119
122
|
|
|
120
123
|
export namespace ChatWidgetFactory {
|
|
@@ -126,6 +129,7 @@ export namespace ChatWidgetFactory {
|
|
|
126
129
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
127
130
|
inputToolbarRegistry?: IInputToolbarRegistry;
|
|
128
131
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
132
|
+
welcomeMessage?: string;
|
|
129
133
|
}
|
|
130
134
|
|
|
131
135
|
export interface IOptions<T extends LabChatPanel>
|
|
@@ -136,6 +140,7 @@ export namespace ChatWidgetFactory {
|
|
|
136
140
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
137
141
|
inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
138
142
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
143
|
+
welcomeMessage?: string;
|
|
139
144
|
}
|
|
140
145
|
}
|
|
141
146
|
|
package/src/model.ts
CHANGED
|
@@ -67,7 +67,8 @@ export class LabChatModel
|
|
|
67
67
|
|
|
68
68
|
this.sharedModel.awareness.on('change', this.onAwarenessChange);
|
|
69
69
|
|
|
70
|
-
this.input.valueChanged.connect(this.onInputChanged);
|
|
70
|
+
this.input.valueChanged.connect((_, value) => this.onInputChanged(value));
|
|
71
|
+
this.messageEditionAdded.connect(this.onMessageEditionAdded);
|
|
71
72
|
}
|
|
72
73
|
|
|
73
74
|
readonly collaborative = true;
|
|
@@ -259,9 +260,12 @@ export class LabChatModel
|
|
|
259
260
|
}
|
|
260
261
|
|
|
261
262
|
/**
|
|
262
|
-
* Function called
|
|
263
|
+
* Function called when the input content changed.
|
|
264
|
+
*
|
|
265
|
+
* @param value - The whole input content.
|
|
266
|
+
* @param messageID - The ID of the message being edited, if any.
|
|
263
267
|
*/
|
|
264
|
-
onInputChanged = (
|
|
268
|
+
onInputChanged = (value: string, messageID?: string): void => {
|
|
265
269
|
if (!value || !this.config.sendTypingNotification) {
|
|
266
270
|
return;
|
|
267
271
|
}
|
|
@@ -269,26 +273,46 @@ export class LabChatModel
|
|
|
269
273
|
if (this._timeoutWriting !== null) {
|
|
270
274
|
window.clearTimeout(this._timeoutWriting);
|
|
271
275
|
}
|
|
272
|
-
awareness.setLocalStateField('isWriting', true);
|
|
276
|
+
awareness.setLocalStateField('isWriting', messageID ?? true);
|
|
273
277
|
this._timeoutWriting = window.setTimeout(() => {
|
|
274
278
|
this._resetWritingStatus();
|
|
275
279
|
}, WRITING_DELAY);
|
|
276
280
|
};
|
|
277
281
|
|
|
282
|
+
/**
|
|
283
|
+
* Listen to the message edition input.
|
|
284
|
+
*/
|
|
285
|
+
onMessageEditionAdded = (
|
|
286
|
+
_: IChatModel,
|
|
287
|
+
edition: IChatModel.IMessageEdition
|
|
288
|
+
) => {
|
|
289
|
+
if (edition !== null) {
|
|
290
|
+
const _onInputChanged = (_: IInputModel, value: string) => {
|
|
291
|
+
this.onInputChanged(value, edition.id);
|
|
292
|
+
};
|
|
293
|
+
|
|
294
|
+
edition.model.valueChanged.connect(_onInputChanged);
|
|
295
|
+
}
|
|
296
|
+
};
|
|
297
|
+
|
|
278
298
|
/**
|
|
279
299
|
* Triggered when an awareness state changes.
|
|
280
300
|
* Used to populate the writers list.
|
|
281
301
|
*/
|
|
282
302
|
onAwarenessChange = () => {
|
|
283
|
-
const writers:
|
|
303
|
+
const writers: IChatModel.IWriter[] = [];
|
|
284
304
|
const states = this.sharedModel.awareness.getStates();
|
|
285
305
|
for (const stateID of states.keys()) {
|
|
286
306
|
const state = states.get(stateID);
|
|
287
307
|
if (!state || !state.user || state.user.username === this.user.username) {
|
|
288
308
|
continue;
|
|
289
309
|
}
|
|
290
|
-
if (state.isWriting) {
|
|
291
|
-
|
|
310
|
+
if (state.isWriting !== undefined && state.isWriting !== false) {
|
|
311
|
+
const writer: IChatModel.IWriter = {
|
|
312
|
+
user: state.user,
|
|
313
|
+
messageID: state.isWriting === true ? undefined : state.isWriting
|
|
314
|
+
};
|
|
315
|
+
writers.push(writer);
|
|
292
316
|
}
|
|
293
317
|
}
|
|
294
318
|
this.updateWriters(writers);
|
package/src/token.ts
CHANGED
|
@@ -144,3 +144,12 @@ export const IInputToolbarRegistryFactory =
|
|
|
144
144
|
new Token<IInputToolbarRegistryFactory>(
|
|
145
145
|
'jupyterlab-chat:IInputToolbarRegistryFactory'
|
|
146
146
|
);
|
|
147
|
+
|
|
148
|
+
/**
|
|
149
|
+
* The token to add a welcome message to the chat.
|
|
150
|
+
* This token is not provided by default, but can be provided by third party extensions
|
|
151
|
+
* willing to add a welcome message to the chat.
|
|
152
|
+
*/
|
|
153
|
+
export const IWelcomeMessage = new Token<string>(
|
|
154
|
+
'jupyterlab-chat:IWelcomeMessage'
|
|
155
|
+
);
|
package/src/widget.tsx
CHANGED
|
@@ -113,6 +113,7 @@ export class ChatPanel extends SidePanel {
|
|
|
113
113
|
this._attachmentOpenerRegistry = options.attachmentOpenerRegistry;
|
|
114
114
|
this._inputToolbarFactory = options.inputToolbarFactory;
|
|
115
115
|
this._messageFooterRegistry = options.messageFooterRegistry;
|
|
116
|
+
this._welcomeMessage = options.welcomeMessage;
|
|
116
117
|
|
|
117
118
|
const addChat = new CommandToolbarButton({
|
|
118
119
|
commands: this._commands,
|
|
@@ -183,7 +184,8 @@ export class ChatPanel extends SidePanel {
|
|
|
183
184
|
chatCommandRegistry: this._chatCommandRegistry,
|
|
184
185
|
attachmentOpenerRegistry: this._attachmentOpenerRegistry,
|
|
185
186
|
inputToolbarRegistry,
|
|
186
|
-
messageFooterRegistry: this._messageFooterRegistry
|
|
187
|
+
messageFooterRegistry: this._messageFooterRegistry,
|
|
188
|
+
welcomeMessage: this._welcomeMessage
|
|
187
189
|
});
|
|
188
190
|
|
|
189
191
|
this.addWidget(
|
|
@@ -306,6 +308,7 @@ export class ChatPanel extends SidePanel {
|
|
|
306
308
|
private _attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
307
309
|
private _inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
308
310
|
private _messageFooterRegistry?: IMessageFooterRegistry;
|
|
311
|
+
private _welcomeMessage?: string;
|
|
309
312
|
}
|
|
310
313
|
|
|
311
314
|
/**
|
|
@@ -325,6 +328,7 @@ export namespace ChatPanel {
|
|
|
325
328
|
attachmentOpenerRegistry?: IAttachmentOpenerRegistry;
|
|
326
329
|
inputToolbarFactory?: IInputToolbarRegistryFactory;
|
|
327
330
|
messageFooterRegistry?: IMessageFooterRegistry;
|
|
331
|
+
welcomeMessage?: string;
|
|
328
332
|
}
|
|
329
333
|
}
|
|
330
334
|
|