diff --git a/mini-program/src/pages/main/ScriptView.vue b/mini-program/src/pages/main/ScriptView.vue index fb8a5c1..b8efc15 100644 --- a/mini-program/src/pages/main/ScriptView.vue +++ b/mini-program/src/pages/main/ScriptView.vue @@ -866,7 +866,7 @@ const keepGenerationAtBottom = () => { } const scrollResultToLatest = () => { - if (viewState.value !== 'result') return + if (viewState.value !== 'result' && viewState.value !== 'chat') return nextTick(() => { measureResultViewport() pushResultScrollCommand(1000000) diff --git a/mini-program/src/services/shortNovel.js b/mini-program/src/services/shortNovel.js index 912440c..b15024c 100644 --- a/mini-program/src/services/shortNovel.js +++ b/mini-program/src/services/shortNovel.js @@ -14,6 +14,7 @@ import { getApiBaseUrl, getAuthHeader } from './request.js' * @returns {Object} uni.request 任务对象(用于 abort) */ export const startNovelStream = ({ query, onEvent, onError }) => { + let chunkProcessed = false const task = uni.request({ url: `${getApiBaseUrl()}/shortNovel/stream`, method: 'POST', @@ -30,7 +31,8 @@ export const startNovelStream = ({ query, onEvent, onError }) => { onError?.(res.data?.message || '请求失败') return } - if (typeof res.data === 'string' && res.data) { + // 仅在 chunk 未处理时才处理完整 data(避免 H5 双重消费) + if (!chunkProcessed && typeof res.data === 'string' && res.data) { consumeSseText(res.data, onEvent, onError) } }, @@ -40,6 +42,7 @@ export const startNovelStream = ({ query, onEvent, onError }) => { }) task?.onChunkReceived?.((res) => { + chunkProcessed = true try { const text = decodeChunk(res.data) consumeSseText(text, onEvent, onError) @@ -62,6 +65,7 @@ export const startNovelStream = ({ query, onEvent, onError }) => { * @returns {Object} uni.request 任务对象 */ export const followupStream = ({ sessionId, action, payload, onEvent, onError }) => { + let chunkProcessed = false const task = uni.request({ url: `${getApiBaseUrl()}/shortNovel/followup`, method: 'POST', @@ -78,7 +82,7 @@ export const followupStream = ({ sessionId, action, payload, onEvent, onError }) onError?.(res.data?.message || '请求失败') return } - if (typeof res.data === 'string' && res.data) { + if (!chunkProcessed && typeof res.data === 'string' && res.data) { consumeSseText(res.data, onEvent, onError) } }, @@ -88,6 +92,7 @@ export const followupStream = ({ sessionId, action, payload, onEvent, onError }) }) task?.onChunkReceived?.((res) => { + chunkProcessed = true try { const text = decodeChunk(res.data) consumeSseText(text, onEvent, onError)