[251030] fix: WebSpeech SilenceDetection disable

🕐 커밋 시간: 2025. 10. 30. 07:12:09

📊 변경 통계:
  • 총 파일: 3개
  • 추가: +72줄
  • 삭제: -54줄

📝 수정된 파일:
  ~ com.twin.app.shoptime/.gitignore
  ~ com.twin.app.shoptime/src/hooks/useReviews/useReviews.js
  ~ com.twin.app.shoptime/src/views/SearchPanel/VoiceInputOverlay/VoiceInputOverlay.jsx

🔧 주요 변경 내용:
  • 핵심 비즈니스 로직 개선
  • 소규모 기능 개선
  • 코드 정리 및 최적화
This commit is contained in:
2025-10-30 07:12:09 +09:00
parent bc35007955
commit f569558a14
3 changed files with 72 additions and 54 deletions

View File

@@ -15,6 +15,10 @@ npm-debug.log
# ipk file
srcBackup
# com.lgshop.app_*.ipk
.doc
.docs
nul
.txt
.optimal
OPTIMAL.md

View File

@@ -28,27 +28,27 @@ const useReviews = (prdtId, patnrId, _deprecatedReviewVersion) => {
// Redux 상태에서 리뷰 데이터 가져오기 - reviewVersion에 따라 선택
const reviewData = useSelector((state) => {
// v2 디버깅: 전체 product state 확인
if (reviewVersion === 2) {
console.log('[useReviews_useReviewList] 📥 전체 Redux state.product 상태:', {
keys: Object.keys(state.product),
reviewData: state.product.reviewData,
reviewListData: state.product.reviewListData,
loadedPrdtId: state.product.loadedPrdtId,
loadedListPrdtId: state.product.loadedListPrdtId
});
}
// if (reviewVersion === 2) {
// console.log('[useReviews_useReviewList] 📥 전체 Redux state.product 상태:', {
// keys: Object.keys(state.product),
// reviewData: state.product.reviewData,
// reviewListData: state.product.reviewListData,
// loadedPrdtId: state.product.loadedPrdtId,
// loadedListPrdtId: state.product.loadedListPrdtId
// });
// }
const data = reviewVersion === 1
? state.product.reviewData
: state.product.reviewListData;
console.log('[useReviews_useReviewList] 📥 Redux reviewData 선택:', {
reviewVersion,
selectedState: reviewVersion === 1 ? 'reviewData' : 'reviewListData',
dataExists: !!data,
dataKeys: data ? Object.keys(data) : 'null',
reviewListLength: data?.reviewList?.length || 0
});
// console.log('[useReviews_useReviewList] 📥 Redux reviewData 선택:', {
// reviewVersion,
// selectedState: reviewVersion === 1 ? 'reviewData' : 'reviewListData',
// dataExists: !!data,
// dataKeys: data ? Object.keys(data) : 'null',
// reviewListLength: data?.reviewList?.length || 0
// });
return data;
});
@@ -58,11 +58,11 @@ const useReviews = (prdtId, patnrId, _deprecatedReviewVersion) => {
? state.product.loadedPrdtId
: state.product.loadedListPrdtId;
console.log('[useReviews_useReviewList] 🔑 Redux loadedPrdtId 선택:', {
reviewVersion,
selectedState: reviewVersion === 1 ? 'loadedPrdtId' : 'loadedListPrdtId',
loadedPrdtId: id
});
// console.log('[useReviews_useReviewList] 🔑 Redux loadedPrdtId 선택:', {
// reviewVersion,
// selectedState: reviewVersion === 1 ? 'loadedPrdtId' : 'loadedListPrdtId',
// loadedPrdtId: id
// });
return id;
});
@@ -647,17 +647,17 @@ const useReviews = (prdtId, patnrId, _deprecatedReviewVersion) => {
totalRatingCount: actualReviewCount, // 실제로 받은 리뷰 개수 사용
};
console.log('[useReviews_useReviewList] 📊 stats 계산:', {
actualReviewCount,
apiTotalCount,
allReviewsLength: allReviews.length,
hasLoadedData,
isLoading,
isCurrentProductLoaded,
reviewVersion,
loadedPrdtId,
prdtId
});
// console.log('[useReviews_useReviewList] 📊 stats 계산:', {
// actualReviewCount,
// apiTotalCount,
// allReviewsLength: allReviews.length,
// hasLoadedData,
// isLoading,
// isCurrentProductLoaded,
// reviewVersion,
// loadedPrdtId,
// prdtId
// });
return result;
}, [allReviews.length, filteredReviews.length, displayReviews.length, reviewDetail, hasLoadedData, isLoading, isCurrentProductLoaded, reviewVersion, loadedPrdtId, prdtId]);
@@ -675,18 +675,18 @@ const useReviews = (prdtId, patnrId, _deprecatedReviewVersion) => {
const hasReviews = allReviews.length > 0 && hasLoadedData && !isLoading && isCurrentProductLoaded;
// hasReviews 계산 로그
useEffect(() => {
console.log('[useReviews_useReviewList] 🔴 hasReviews 계산:', {
allReviewsLength: allReviews.length,
hasLoadedData,
isLoading,
isCurrentProductLoaded,
loadedPrdtId,
prdtId,
resultHasReviews: hasReviews,
reviewVersion
});
}, [hasReviews, allReviews.length, hasLoadedData, isLoading, isCurrentProductLoaded, loadedPrdtId, prdtId, reviewVersion]);
// useEffect(() => {
// console.log('[useReviews_useReviewList] 🔴 hasReviews 계산:', {
// allReviewsLength: allReviews.length,
// hasLoadedData,
// isLoading,
// isCurrentProductLoaded,
// loadedPrdtId,
// prdtId,
// resultHasReviews: hasReviews,
// reviewVersion
// });
// }, [hasReviews, allReviews.length, hasLoadedData, isLoading, isCurrentProductLoaded, loadedPrdtId, prdtId, reviewVersion]);
return {
// 🔥 핵심 API 함수 - useReviews가 모든 API 호출 담당

View File

@@ -95,6 +95,11 @@ const DEFAULT_SUGGESTIONS = [
// false로 설정하면 이 기능은 완전히 비활성화됩니다
const ENABLE_WAKE_WORD = false;
// 🔧 Silence Detection 활성화 여부
// continuous: true에서 노이즈를 interim으로 감지할 수 있어
// 사용자가 준비 단계에서 조기 종료될 수 있으므로 false로 설정
const IS_SILENCE_CHECK_ENABLED = false;
// Utility function to clear a single timer ref (timeout)
const clearTimerRef = (timerRef) => {
if (timerRef.current) {
@@ -852,29 +857,38 @@ const VoiceInputOverlay = ({
// }
// }, [voiceInputMode, currentMode, isListening, startListening, stopListening]);
// 🎤 Interim 텍스트 실시간 표시 및 ref 업데이트 + 3초 silence detection
// 🎤 Interim 텍스트 실시간 표시 및 ref 업데이트
// Silence Detection은 IS_SILENCE_CHECK_ENABLED에 따라 제어
useEffect(() => {
if (currentMode !== VOICE_MODES.LISTENING) {
// ✅ LISTENING 모드가 아니면 타이머 정리
clearTimerRef(silenceDetectionTimerRef);
silenceDetectionTimerRef.current = null;
if (IS_SILENCE_CHECK_ENABLED) {
clearTimerRef(silenceDetectionTimerRef);
silenceDetectionTimerRef.current = null;
}
return;
}
// ✅ Ref 업데이트 (15초 타이머에서 최신 값을 읽을 수 있도록)
interimTextRef.current = interimText || '';
// ✨ TInput에 실시간으로 텍스트 표시
if (onSearchChange && interimText) {
onSearchChange({ value: interimText });
}
// ✅ Silence Detection (IS_SILENCE_CHECK_ENABLED === true일 때만)
if (!IS_SILENCE_CHECK_ENABLED) {
// Silence Detection 비활성화 - 15초 타이머에만 의존
return;
}
if (!interimText) {
// 입력이 없으면 silence detection 시작하지 않음
return;
}
// ✨ TInput에 실시간으로 텍스트 표시
if (onSearchChange) {
onSearchChange({ value: interimText });
}
// ✅ 3초 silence detection: 마지막 입력 후 3초 동안 추가 입력이 없으면 자동 종료
// 3초 silence detection: 마지막 입력 후 3초 동안 추가 입력이 없으면 자동 종료
clearTimerRef(silenceDetectionTimerRef);
silenceDetectionTimerRef.current = setTimeout(() => {
console.log('[VoiceInput] 🔇 3초 동안 입력 없음 - 자동 종료');
@@ -887,7 +901,7 @@ const VoiceInputOverlay = ({
clearTimerRef(silenceDetectionTimerRef);
silenceDetectionTimerRef.current = null;
};
}, [interimText, currentMode, onSearchChange, processFinalVoiceInput, addWebSpeechEventLog]);
}, [interimText, currentMode, onSearchChange, processFinalVoiceInput, addWebSpeechEventLog, IS_SILENCE_CHECK_ENABLED]);
// 🎉 Wake Word Detection: PROMPT 모드에서 백그라운드 리스닝 시작
useEffect(() => {