@lvce-editor/chat-view 6.2.0 → 6.3.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.
@@ -5870,9 +5870,6 @@ const parseBoldToken = (value, start) => {
5870
5870
  const findItalicEnd = (value, start) => {
5871
5871
  let index = start + 1;
5872
5872
  while (index < value.length) {
5873
- if (value[index] === '\n') {
5874
- return -1;
5875
- }
5876
5873
  if (value[index] !== '*') {
5877
5874
  index++;
5878
5875
  continue;
@@ -5897,7 +5894,7 @@ const parseItalicToken = (value, start) => {
5897
5894
  return undefined;
5898
5895
  }
5899
5896
  const text = value.slice(start + 1, end);
5900
- if (!text || text.includes('\n')) {
5897
+ if (!text) {
5901
5898
  return undefined;
5902
5899
  }
5903
5900
  return {
@@ -5928,6 +5925,26 @@ const parseStrikethroughToken = (value, start) => {
5928
5925
  }
5929
5926
  };
5930
5927
  };
5928
+ const parseInlineCodeToken = (value, start) => {
5929
+ if (value[start] !== '`') {
5930
+ return undefined;
5931
+ }
5932
+ const end = value.indexOf('`', start + 1);
5933
+ if (end === -1) {
5934
+ return undefined;
5935
+ }
5936
+ const codeText = value.slice(start + 1, end);
5937
+ if (!codeText || codeText.includes('\n')) {
5938
+ return undefined;
5939
+ }
5940
+ return {
5941
+ length: end - start + 1,
5942
+ node: {
5943
+ text: codeText,
5944
+ type: 'inline-code'
5945
+ }
5946
+ };
5947
+ };
5931
5948
  const parseMathToken = (value, start) => {
5932
5949
  if (value[start] !== '$') {
5933
5950
  return undefined;
@@ -5974,7 +5991,7 @@ const parseMathToken = (value, start) => {
5974
5991
  return undefined;
5975
5992
  };
5976
5993
  const parseInlineToken = (value, start) => {
5977
- return parseImageToken(value, start) || parseLinkToken(value, start) || parseBoldToken(value, start) || parseItalicToken(value, start) || parseLinkToken(value, start) || parseBoldToken(value, start) || parseItalicToken(value, start) || parseStrikethroughToken(value, start) || parseMathToken(value, start);
5994
+ return parseImageToken(value, start) || parseLinkToken(value, start) || parseBoldToken(value, start) || parseItalicToken(value, start) || parseLinkToken(value, start) || parseBoldToken(value, start) || parseItalicToken(value, start) || parseStrikethroughToken(value, start) || parseInlineCodeToken(value, start) || parseMathToken(value, start);
5978
5995
  };
5979
5996
  const parseInlineNodes = value => {
5980
5997
  const nodes = [];
@@ -6299,7 +6316,6 @@ const parseBlockTokens = tokens => {
6299
6316
  for (let i = 0; i < tokens.length; i++) {
6300
6317
  const token = tokens[i];
6301
6318
  if (token.type === 'blank-line') {
6302
- flushList();
6303
6319
  flushParagraph();
6304
6320
  continue;
6305
6321
  }
@@ -6842,6 +6858,33 @@ const getSseEventType = value => {
6842
6858
  return value && typeof value === 'object' && Reflect.get(value, 'type') === 'response.completed' ? 'sse-response-completed' : 'sse-response-part';
6843
6859
  };
6844
6860
 
6861
+ const getToolCallMergeKey = toolCall => {
6862
+ if (toolCall.id) {
6863
+ return `id:${toolCall.id}`;
6864
+ }
6865
+ return `value:${toolCall.name}:${toolCall.arguments}`;
6866
+ };
6867
+ const mergeToolCalls = (existing = [], incoming) => {
6868
+ if (incoming.length === 0) {
6869
+ return existing;
6870
+ }
6871
+ const merged = [...existing];
6872
+ const indexByKey = new Map();
6873
+ for (let i = 0; i < merged.length; i++) {
6874
+ indexByKey.set(getToolCallMergeKey(merged[i]), i);
6875
+ }
6876
+ for (const toolCall of incoming) {
6877
+ const key = getToolCallMergeKey(toolCall);
6878
+ const existingIndex = indexByKey.get(key);
6879
+ if (existingIndex === undefined) {
6880
+ indexByKey.set(key, merged.length);
6881
+ merged.push(toolCall);
6882
+ continue;
6883
+ }
6884
+ merged[existingIndex] = toolCall;
6885
+ }
6886
+ return merged;
6887
+ };
6845
6888
  const updateMessageTextInSelectedSession = async (sessions, parsedMessages, selectedSessionId, messageId, text, inProgress) => {
6846
6889
  let updatedMessage;
6847
6890
  const updatedSessions = sessions.map(session => {
@@ -6886,7 +6929,7 @@ const updateMessageToolCallsInSelectedSession = (sessions, parsedMessages, selec
6886
6929
  }
6887
6930
  const updatedMessage = {
6888
6931
  ...message,
6889
- toolCalls
6932
+ toolCalls: mergeToolCalls(message.toolCalls, toolCalls)
6890
6933
  };
6891
6934
  nextParsedMessages = copyParsedMessageContent(nextParsedMessages, message.id, updatedMessage.id);
6892
6935
  return updatedMessage;
@@ -7743,6 +7786,13 @@ const handleMessagesContextMenu = async state => {
7743
7786
  return state;
7744
7787
  };
7745
7788
 
7789
+ const handleMissingApiKeySubmit = async (state, submitterName = '') => {
7790
+ if (!submitterName) {
7791
+ return state;
7792
+ }
7793
+ return handleClick(state, submitterName);
7794
+ };
7795
+
7746
7796
  const handleModelChange = async (state, value) => {
7747
7797
  return {
7748
7798
  ...state,
@@ -8723,6 +8773,7 @@ const HandleDragOverChatView = 31;
8723
8773
  const HandleProjectListScroll = 32;
8724
8774
  const HandleProjectListContextMenu = 33;
8725
8775
  const HandleClickDictationButton = 34;
8776
+ const HandleMissingApiKeySubmit = 35;
8726
8777
 
8727
8778
  const getModelLabel = model => {
8728
8779
  if (model.provider === 'openRouter') {
@@ -8889,6 +8940,12 @@ const getInlineNodeDom = (inlineNode, useChatMathWorker = false) => {
8889
8940
  type: Span
8890
8941
  }, ...inlineNode.children.flatMap(child => getInlineNodeDom(child, useChatMathWorker))];
8891
8942
  }
8943
+ if (inlineNode.type === 'inline-code') {
8944
+ return [{
8945
+ childCount: 1,
8946
+ type: Code
8947
+ }, text(inlineNode.text)];
8948
+ }
8892
8949
  if (inlineNode.type === 'math-inline') {
8893
8950
  const fallback = inlineNode.displayMode ? `$$${inlineNode.text}$$` : `$${inlineNode.text}$`;
8894
8951
  return [text(fallback)];
@@ -8970,6 +9027,22 @@ const cssRules = [{
8970
9027
  className: TokenProperty,
8971
9028
  regex: /[a-zA-Z-]+(?=\s*:)/
8972
9029
  }];
9030
+ const pythonRules = [{
9031
+ className: TokenComment,
9032
+ regex: /#[^\n]*/
9033
+ }, {
9034
+ className: TokenString,
9035
+ regex: /"[^"\\]*(?:\\.[^"\\]*)*"/
9036
+ }, {
9037
+ className: TokenString,
9038
+ regex: /'[^'\\]*(?:\\.[^'\\]*)*'/
9039
+ }, {
9040
+ className: TokenNumber,
9041
+ regex: /\b\d+\.?\d*\b/
9042
+ }, {
9043
+ className: TokenKeyword,
9044
+ regex: /\b(?:def|class|return|if|elif|else|for|while|in|import|from|as|with|try|except|finally|raise|lambda|yield|pass|break|continue|True|False|None|and|or|not|is)\b/
9045
+ }];
8973
9046
  const tokenize = (code, rules) => {
8974
9047
  const tokens = [];
8975
9048
  let pos = 0;
@@ -9023,6 +9096,9 @@ const highlightCode = (code, language) => {
9023
9096
  if (normalized === 'js' || normalized === 'javascript') {
9024
9097
  return tokenize(code, jsRules);
9025
9098
  }
9099
+ if (normalized === 'py' || normalized === 'python') {
9100
+ return tokenize(code, pythonRules);
9101
+ }
9026
9102
  return [{
9027
9103
  className: '',
9028
9104
  text: code
@@ -9197,6 +9273,8 @@ const getMissingApiKeyDom = ({
9197
9273
  }) => {
9198
9274
  return [{
9199
9275
  childCount: 2,
9276
+ method: useForm ? 'GET' : undefined,
9277
+ onSubmit: useForm ? HandleMissingApiKeySubmit : undefined,
9200
9278
  type: useForm ? Form : Div
9201
9279
  }, {
9202
9280
  childCount: 0,
@@ -9218,7 +9296,7 @@ const getMissingApiKeyDom = ({
9218
9296
  className: mergeClassNames(Button, ButtonPrimary),
9219
9297
  disabled: saveButtonDisabled,
9220
9298
  name: saveButtonName,
9221
- onClick: HandleClick,
9299
+ onClick: useForm ? undefined : HandleClick,
9222
9300
  type: Button$1
9223
9301
  }, text(saveButtonText), {
9224
9302
  childCount: 1,
@@ -9255,7 +9333,9 @@ const getMissingOpenRouterApiKeyDom = (openRouterApiKeyInput, openRouterApiKeySt
9255
9333
  placeholder: openRouterApiKeyPlaceholder(),
9256
9334
  saveButtonDisabled: isSaving,
9257
9335
  saveButtonName: SaveOpenRouterApiKey,
9258
- saveButtonText: isSaving ? saving() : save()
9336
+ saveButtonText: isSaving ? saving() : save(),
9337
+ saveButtonType: 'submit',
9338
+ useForm: true
9259
9339
  });
9260
9340
  };
9261
9341
 
@@ -10259,7 +10339,19 @@ const renderItems = (oldState, newState) => {
10259
10339
  return [SetDom2, uid, dom];
10260
10340
  };
10261
10341
 
10342
+ const getSelectedSessionToolCallSignature = state => {
10343
+ const selectedSession = state.sessions.find(session => session.id === state.selectedSessionId);
10344
+ if (!selectedSession) {
10345
+ return '';
10346
+ }
10347
+ return selectedSession.messages.map(message => `${message.id}:${JSON.stringify(message.toolCalls || [])}`).join('|');
10348
+ };
10262
10349
  const renderIncremental = (oldState, newState) => {
10350
+ const oldToolCallSignature = getSelectedSessionToolCallSignature(oldState);
10351
+ const newToolCallSignature = getSelectedSessionToolCallSignature(newState);
10352
+ if (oldToolCallSignature !== newToolCallSignature) {
10353
+ return renderItems(oldState, newState);
10354
+ }
10263
10355
  const oldDom = renderItems(oldState, oldState)[2];
10264
10356
  const newDom = renderItems(newState, newState)[2];
10265
10357
  const patches = diffTree(oldDom, newDom);
@@ -10473,6 +10565,10 @@ const renderEventListeners = () => {
10473
10565
  }, {
10474
10566
  name: HandleSubmit,
10475
10567
  params: ['handleSubmit']
10568
+ }, {
10569
+ name: HandleMissingApiKeySubmit,
10570
+ params: ['handleMissingApiKeySubmit', 'event.submitter?.name || ""'],
10571
+ preventDefault: true
10476
10572
  }];
10477
10573
  };
10478
10574
 
@@ -10658,6 +10754,7 @@ const commandMap = {
10658
10754
  'Chat.handleKeyDown': wrapCommand(handleKeyDown),
10659
10755
  'Chat.handleMessagesContextMenu': wrapCommand(handleMessagesContextMenu),
10660
10756
  'Chat.handleMessagesScroll': wrapCommand(handleMessagesScroll),
10757
+ 'Chat.handleMissingApiKeySubmit': wrapCommand(handleMissingApiKeySubmit),
10661
10758
  'Chat.handleModelChange': wrapCommand(handleModelChange),
10662
10759
  'Chat.handleProjectListContextMenu': wrapCommand(handleProjectListContextMenu),
10663
10760
  'Chat.handleProjectListScroll': wrapCommand(handleProjectListScroll),
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lvce-editor/chat-view",
3
- "version": "6.2.0",
3
+ "version": "6.3.0",
4
4
  "description": "Chat View Worker",
5
5
  "repository": {
6
6
  "type": "git",