94 lines
3.4 KiB
JavaScript
94 lines
3.4 KiB
JavaScript
import React, { createContext, useState, useContext, useEffect } from 'react';
|
|
import { API_BASE_URL } from '../config';
|
|
|
|
const ToolContext = createContext();
|
|
|
|
export function ToolProvider({ children }) {
|
|
const [tools, setTools] = useState([]);
|
|
const [selectedTool, setSelectedTool] = useState(null);
|
|
const [favorites, setFavorites] = useState(() => {
|
|
try {
|
|
return JSON.parse(localStorage.getItem('favorites')) || [];
|
|
} catch {
|
|
return [];
|
|
}
|
|
});
|
|
|
|
useEffect(() => {
|
|
async function load() {
|
|
try {
|
|
const res = await fetch(`${API_BASE_URL}/tools`);
|
|
const data = await res.json();
|
|
// 'GxP 챗봇'과 'chatgpt' 카드는 도구 목록에서 제거
|
|
const filtered = (Array.isArray(data) ? data : []).filter((tool) => !['chatbot_gxp','chatgpt','lims_text2sql','research_qa'].includes(tool.id));
|
|
const mapped = filtered.map((tool) => {
|
|
const category = ['전체'];
|
|
if (['dev_chatbot', 'doc_translation'].includes(tool.id)) {
|
|
category.push('오픈AI');
|
|
}
|
|
return { ...tool, category };
|
|
});
|
|
setTools(mapped);
|
|
// 선택된 도구 복원 (마지막 카드 유지)
|
|
try {
|
|
const savedId = localStorage.getItem('selectedToolId');
|
|
if (savedId) {
|
|
const found = mapped.find((t) => t.id === savedId);
|
|
if (found) setSelectedTool(found);
|
|
}
|
|
// URL 경로가 카드 ID일 경우 해당 카드로 강제 설정 (예: /dev_chatbot)
|
|
const path = window.location.pathname.replace(/^\/+/, '');
|
|
const menuPaths = new Set(['chatting', 'tools', 'lecture', 'community', '']);
|
|
if (path && !menuPaths.has(path)) {
|
|
const fromUrl = mapped.find((t) => t.id === path);
|
|
if (fromUrl) setSelectedTool(fromUrl);
|
|
}
|
|
} catch {}
|
|
// 즐겨찾기에 남아 있을 수 있는 제거 대상 정리
|
|
setFavorites((prev) => prev.filter((id) => !['chatbot_gxp','chatgpt','lims_text2sql','research_qa'].includes(id)));
|
|
} catch (_) {}
|
|
}
|
|
load();
|
|
}, []);
|
|
|
|
useEffect(() => {
|
|
localStorage.setItem('favorites', JSON.stringify(favorites));
|
|
}, [favorites]);
|
|
|
|
// 선택된 도구 지속화: 메뉴 이동 후에도 마지막 카드가 유지되도록 저장
|
|
useEffect(() => {
|
|
try {
|
|
if (selectedTool?.id) localStorage.setItem('selectedToolId', selectedTool.id);
|
|
} catch {}
|
|
}, [selectedTool?.id]);
|
|
|
|
const toggleFavorite = (id) => {
|
|
setFavorites((prev) => (prev.includes(id) ? prev.filter((f) => f !== id) : [...prev, id]));
|
|
};
|
|
|
|
// 카드 선택 시 URL을 카드 경로로 반영 (메뉴 페이지가 아닌 경우)
|
|
useEffect(() => {
|
|
if (!selectedTool?.id) return;
|
|
const path = `/${selectedTool.id}`;
|
|
const menuPaths = new Set(['/chatting','/tools','/lecture','/community','/']);
|
|
if (!menuPaths.has(window.location.pathname) && window.location.pathname === path) return;
|
|
// 도구 화면에서 카드 선택 시 URL을 카드 경로로 업데이트
|
|
if (window.location.pathname !== path) {
|
|
window.history.pushState({}, '', path);
|
|
}
|
|
}, [selectedTool?.id]);
|
|
|
|
const value = {
|
|
tools,
|
|
selectedTool,
|
|
setSelectedTool,
|
|
favorites,
|
|
toggleFavorite,
|
|
};
|
|
|
|
return <ToolContext.Provider value={value}>{children}</ToolContext.Provider>;
|
|
}
|
|
|
|
export function useTool() {
|
|
return useContext(ToolContext);
|
|
}
|