Skip to content
Snippets Groups Projects
Select Git revision
  • ccf83bf4c370fbfa7232aec9a97bbf60dfb5e272
  • master default protected
2 results

App.js

Blame
  • App.js 5.60 KiB
    import React, { useEffect } from 'react';
    import SearchPage from './SearchPage';
    import Favorites from './Favorites';
    import MusicList from './MusicList';
    import SnackMsg from './SnackMsg';
    import {Box, Tabs, Tab, Typography, AppBar} from '@mui/material';
    import { LineAxisOutlined } from '@mui/icons-material';
    
    export default function App () {
        const [currentTab, setCurrentTab] = React.useState(0);//탭
        const [searchResult, setSearchResult] = React.useState([]);//서치결과
        
        const [likes, setLikes] = React.useState({});//좋아요결과
        const [snackState, setSnackState] = React.useState({open: false, msg:''})//스낵바열림결과
        const [favorites, setFavorites] = React.useState([]);//재검색해도 Favorites목록이 리셋되는 것을 막기 위해 Favorites 모아놓은 상태변수 만듦
    
        //여기에 useEffect로 favorites랑 likes관리?  
        //사이트 처음 들어갈 때 좋아요 목록이랑 좋아요 표시가 잘 나타나도록
        useEffect(() => {
            fetch(`/likes`, {method:'GET'})
            .then((r) => r.json())
            .then((r) => {setFavorites(r), setLikes(r);})
            .catch((error) => {
                console.error("Error fetching favorites:", error);
            });         
      }, []);  
                
        const handleTabChange = (event, newValue) => {//탭
            setCurrentTab(newValue);
        }
    
        const toggleFavorite = (id, name) => {//좋아요와 스낵바 상태 업데이트
            setSnackState({open: true, msg: `${name} is clicked`})
            
            if (likes[id]) {//이미 좋아요를 한 item이라면
                fetch(`/likes/${id}`, {method: "DELETE"})//fetch 기능을 사용하여 서버에 대한 네트워크 요청을 보냄
                    .then((r)=>r.json())
                    .then((r)=>{
                        console.log(r);
                        console.log("DELETE");
                        setLikes(prevLikes => ({...prevLikes, [id]: !prevLikes[id]}));//기존의 모든 키-값 쌍을 복사한다음 뒤에 써져있는대로 업데이트함
                        setFavorites(prevFavorites => prevFavorites.filter(item => item.collectionId !== id));
                    })
                    .catch((error) => {
                        console.error('Error deleting likes:', error);
                    });
            }
            //참고 코드
            /*
            @GetMapping(value="/likes")
            public List<FavoriteMusic> getLikes() {
                return service.getLikes();
            }
    
            @PostMapping(value="/likes")
            public int postLikes(@RequestBody FavoriteMusicRequestDto favorite) {
                return service.saveFavorite(favorite);
            } 
    
            @DeleteMapping(value="/likes/{id}")
            public int deleteLikes(@PathVariable String id) {
                return service.deleteFavorite(id);
            }
            */
            /*
            fetch(`/musicSearch/${searchWord}`)//fetch 기능을 사용하여 서버에 대한 네트워크 요청을 보냄
            .then(r => r.json()).then(r => {
                console.log(r);
                onSearch(r.results);
                setSearchWord('');//searchWord 변수 값을 다시 빈 문자열로 초기화
            }).catch(e => console.log('error when search musician));
            */
            else {//좋아요가 아직 안 되어있는 item이라면
                const selectedItem = searchResult.find(item => item.collectionId === id);
                if (selectedItem) {
                    fetch(`/likes`, {method: "POST", headers: {'Content-Type': 'application/json'}, body: JSON.stringify(item)})//fetch 기능을 사용하여 서버에 대한 네트워크 요청을 보냄
                        .then((r)=>r.json())
                        .then((r)=>{
                            console.log(r);
                            console.log("POST");
                            setLikes(prevLikes => ({ ...prevLikes, [id]: !prevLikes[id] }));
                            setFavorites(prevFavorites => [...prevFavorites, selectedItem]);
                        })
                        .catch((error) => {
                            console.error('Error posting likes:', error);
                        });
                }
    
            }
        }
    
        const handleSnackbarClose = (event, reason)=> {//스낵바 닫기
            if(reason === 'clickaway'){
                return;
            }
            setSnackState({open: false, msg: ''});
        }
        
        return (
            <React.Fragment>
                <AppBar positions = "fixed">
                    <Typography align = "center" variant = "h3" color = "inherit">Hyunjin's Favorite Music</Typography>
                </AppBar>
    
                <div style = {{height: 60, width: '100%'}}></div>
                <Box sx = {{borderBottom: 1, borderColor: 'divider'}}>
                    <Tabs value = {currentTab} onChange = {handleTabChange} aria-label = "basic tabs" centered>
                        <Tab label = "Search Music" value = {0}/>
                        <Tab label = "Favorites" value = {1}/>
                        <Tab label = "More Contents" value = {2}/>
                    </Tabs>
                </Box>
                {currentTab == 0 && 
                <>
                <SearchPage onSearch = {setSearchResult}/> 
                <MusicList list = {searchResult} likes = {likes} toggleFavorite = {toggleFavorite}/>
                </>
                }
                {currentTab == 1 && 
                <>
                <Typography align = "center" variant = "h5"> Favorites </Typography>
                <Favorites list = {favorites} likes = {likes} toggleFavorite = {toggleFavorite}/>
                </>}
                {currentTab == 2 && <Typography align = "center" variant = "h5"> More Contents </Typography>}
                <SnackMsg open = {snackState.open} message = {snackState.msg} onClose = {handleSnackbarClose}/>
            </React.Fragment>
        )    
    }