묻고 답해요
158만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
미해결Next + React Query로 SNS 서비스 만들기
서로 다른 컴포넌트간 query 일치하게 하기 강의중
안녕하세여 제로초님 UserInfo에서 팔로우버튼을 누르면 팔로잉으로 변해야되고 다시 한번 누르면 팔로우로 변해야되는데 버튼을 누르고 새로고침을 해야지만 반영이됩니다... 팔로우 추천에서는 바로 반영이 되는데....깃허브 ch3-2 UserInfo에 있는 코드로 가져다 써도 안되네여 ㅠㅠ"use client"; import style from "@/app/(afterLogin)/[username]/profile.module.css"; import BackButton from "@/app/(afterLogin)/_component/BackButton"; import { useQuery, useQueryClient, useMutation } from "@tanstack/react-query"; import { User } from "@/model/User"; import { getUser } from "@/app/(afterLogin)/[username]/_lib/getUser"; import cx from "classnames"; import { MouseEventHandler } from "react"; import { Session } from "@auth/core/types"; type Props = { username: string; session: Session | null; }; export default function UserInfo({ username, session }: Props) { const { data: user, error } = useQuery< User, Object, User, [_1: string, _2: string] >({ queryKey: ["users", username], queryFn: getUser, staleTime: 60 * 1000, // fresh -> stale, 5분이라는 기준 gcTime: 300 * 1000, }); const queryClient = useQueryClient(); const follow = useMutation({ mutationFn: (userId: string) => { console.log("follow", userId); return fetch( `${process.env.NEXT_PUBLIC_BASE_URL}/api/users/${userId}/follow`, { credentials: "include", method: "post", } ); }, onMutate(userId: string) { const value: User[] | undefined = queryClient.getQueryData([ "users", "followRecommends", ]); if (value) { const index = value.findIndex((v) => v.id === userId); if (index > -1) { console.log(value, userId, index); const shallow = [...value]; shallow[index] = { ...shallow[index], Followers: [{ id: session?.user?.email as string }], _count: { ...shallow[index]._count, Followers: shallow[index]._count?.Followers + 1, }, }; queryClient.setQueryData(["users", "followRecommends"], shallow); } } const value2: User | undefined = queryClient.getQueryData([ "users", userId, ]); if (value2) { const shallow: User = { ...value2, Followers: [{ id: session?.user?.email as string }], _count: { ...value2._count, Followers: value2._count?.Followers + 1, }, }; queryClient.setQueryData(["users", userId], shallow); } }, onError(error, userId: string) { console.error(error); const value: User[] | undefined = queryClient.getQueryData([ "users", "followRecommends", ]); if (value) { const index = value.findIndex((v) => v.id === userId); console.log(value, userId, index); if (index > -1) { const shallow = [...value]; shallow[index] = { ...shallow[index], Followers: shallow[index].Followers.filter( (v) => v.id !== session?.user?.email ), _count: { ...shallow[index]._count, Followers: shallow[index]._count?.Followers - 1, }, }; queryClient.setQueryData(["users", "followRecommends"], shallow); } const value2: User | undefined = queryClient.getQueryData([ "users", userId, ]); if (value2) { const shallow = { ...value2, Followers: value2.Followers.filter( (v) => v.id !== session?.user?.email ), _count: { ...value2._count, Followers: value2._count?.Followers - 1, }, }; queryClient.setQueryData(["users", userId], shallow); } } }, }); const unfollow = useMutation({ mutationFn: (userId: string) => { console.log("unfollow", userId); return fetch( `${process.env.NEXT_PUBLIC_BASE_URL}/api/users/${userId}/follow`, { credentials: "include", method: "delete", } ); }, onMutate(userId: string) { const value: User[] | undefined = queryClient.getQueryData([ "users", "followRecommends", ]); if (value) { const index = value.findIndex((v) => v.id === userId); console.log(value, userId, index); if (index > -1) { const shallow = [...value]; shallow[index] = { ...shallow[index], Followers: shallow[index].Followers.filter( (v) => v.id !== session?.user?.email ), _count: { ...shallow[index]._count, Followers: shallow[index]._count?.Followers - 1, }, }; queryClient.setQueryData(["users", "followRecommends"], shallow); } const value2: User | undefined = queryClient.getQueryData([ "users", userId, ]); if (value2) { const shallow = { ...value2, Followers: value2.Followers.filter( (v) => v.id !== session?.user?.email ), _count: { ...value2._count, Followers: value2._count?.Followers - 1, }, }; queryClient.setQueryData(["users", userId], shallow); } } }, onError(error, userId: string) { console.error(error); const value: User[] | undefined = queryClient.getQueryData([ "users", "followRecommends", ]); if (value) { const index = value.findIndex((v) => v.id === userId); console.log(value, userId, index); if (index > -1) { const shallow = [...value]; shallow[index] = { ...shallow[index], Followers: [{ id: session?.user?.email as string }], _count: { ...shallow[index]._count, Followers: shallow[index]._count?.Followers + 1, }, }; queryClient.setQueryData(["users", "followRecommends"], shallow); } } const value2: User | undefined = queryClient.getQueryData([ "users", userId, ]); if (value2) { const shallow = { ...value2, Followers: [{ userId: session?.user?.email as string }], _count: { ...value2._count, Followers: value2._count?.Followers + 1, }, }; queryClient.setQueryData(["users", userId], shallow); } }, }); console.log("error"); console.dir(error); if (error) { return ( <> <div className={style.header}> <BackButton /> <h3 className={style.headerTitle}>프로필</h3> </div> <div className={style.userZone}> <div className={style.userImage}></div> <div className={style.userName}> <div>@{username}</div> </div> </div> <div style={{ height: 100, alignItems: "center", fontSize: 31, fontWeight: "bold", justifyContent: "center", display: "flex", }} > 계정이 존재하지 않음 </div> </> ); } if (!user) { return null; } const followed = user.Followers?.find((v) => v.id === session?.user?.email); console.log(session?.user?.email, followed); const onFollow: MouseEventHandler<HTMLButtonElement> = (e) => { e.stopPropagation(); e.preventDefault(); console.log("follow", followed, user.id); if (followed) { unfollow.mutate(user.id); } else { follow.mutate(user.id); } }; return ( <> <div className={style.header}> <BackButton /> <h3 className={style.headerTitle}>{user.nickname}</h3> </div> <div className={style.userZone}> <div className={style.userRow}> <div className={style.userImage}> <img src={user.image} alt={user.id} /> </div> <div className={style.userName}> <div>{user.nickname}</div> <div>@{user.id}</div> </div> {user.id !== session?.user?.email && ( <button onClick={onFollow} className={cx(style.followButton, followed && style.followed)} > {followed ? "팔로잉" : "팔로우"} </button> )} </div> <div className={style.userFollower}> <div>{user._count.Followers} 팔로워</div> <div>{user._count.Followings} 팔로우 중</div> </div> </div> </> ); }제가 보기에는 useQuery가 제대로 작동안하는거같은데...제로초님 의견이 궁금합니다팔로우버튼 안눌렀을때 팔로우버튼 눌렀을때
-
미해결홍정모의 따라하며 배우는 C언어
커리큘럼 관련 질문
안녀하세요 맨 마지막 따라하며 배우는 프로그래밍에서 C -> 코딩수학 C+ ->>> 딥러닝 순으로 나열 해 주셨는데 이 순서가 최적의 커리큘럼으로 정해진 순서로 이해하면될까요??
-
해결됨실리콘밸리 엔지니어가 가르치는 파이썬 기초부터 고급까지
수업 때 쓰셨던 txt file 공유 해주시면 좋겠습니다
나라 이름, 도시 같은 것들은 영상 아래 강의 노트에서 복붙할 수 있으면 좋겠네요원활한 답변을 위해, 자세한 질문 사항 부탁드려요 :D
-
해결됨비전공자도 이해할 수 있는 CI/CD 입문·실전
도커 이미지 푸시까지는 성공하나, ssh에서 fail이 나옵니다.
강의 및 노션에 있는 부분을 최대한 응용해서, next.js app을 생성중입니다.ecr 저장소에서 도커 이미지가 확실히 푸시되었지만, ssh접속에서 에러가 발생했습니다.======CMD====== docker stop instagram-server || true docker rm instagram-server || true docker pull 767398114270.dkr.ecr.ap-northeast-2.amazonaws.com/instagram-server:latest docker run -d --name instagram-server -p 3000:3000 767398114270.dkr.ecr.ap-northeast-2.amazonaws.com/instagram-server:latest ======END====== err: permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock: Post "http://%2Fvar%2Frun%2Fdocker.sock/v1.44/containers/instagram-server/stop": dial unix /var/run/docker.sock: connect: permission denied err: permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock: Delete "http://%2Fvar%2Frun%2Fdocker.sock/v1.44/containers/instagram-server": dial unix /var/run/docker.sock: connect: permission denied err: permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock: Post "http://%2Fvar%2Frun%2Fdocker.sock/v1.44/images/create?fromImage=767398114270.dkr.ecr.ap-northeast-2.amazonaws.com%2Finstagram-server&tag=latest": dial unix /var/run/docker.sock: connect: permission denied 2024/08/13 11:11:21 Process exited with status 1그래서 workflow를 수정했는데, 밑에 처럼 진행하니 정상처리가 되었습니다.- name: SSH로 EC2에 접속하기 uses: appleboy/ssh-action@v1.0.3 with: host: ${{ secrets.EC2_HOST }} # 인스턴스의 퍼블릭 IP 또는 DNS 이름 username: ${{ secrets.EC2_USERNAME }} # 일반적으로 'ubuntu' 또는 'ec2-user' key: ${{ secrets.EC2_PRIVATE_KEY }} # SSH 개인 키 script_stop: true script: | aws ecr get-login-password --region ap-northeast-2 | sudo docker login --username AWS --password-stdin ${{ steps.login-ecr.outputs.registry }} sudo docker stop instagram-server || true sudo docker rm instagram-server || true sudo docker pull ${{ steps.login-ecr.outputs.registry }}/instagram-server:latest sudo docker run -d --name instagram-server -p 3000:3000 ${{ steps.login-ecr.outputs.registry }}/instagram-server:latest혹시 제가 실수하거나 놓친 부분이있을까요??
-
해결됨Flutter로 웹 서비스 개발하기 (1) - Responsive Web
그리고 또 다른 질문~
이후의 강의 일정은 언제쯤 잡고 계신가요?플러터에서의 SEO강의 너무 듣고 싶어요.. ㅎㅎㅎ
-
미해결
안녕하세요~ 강의에 대한 소스가 안보여요
강의를 들었는데... github소스라든지 그런게 안보이든데...결제했는 사람조차도 소스 제공이 안되나용?답변 부탁드립니당~
-
미해결운영체제 공룡책 강의
java 소켓 통신 예제 질문
DateClient 클래스에서 소켓을 생성하면서 ip address와 포트 번호를 넘겨줄 때, 127.0.0.1 대신 cmd 창에서 ipconfig 명령어로 확인한 IPV4 주소를 입력하면 정상적으로 작동하지 않는데, 왜 그런 건지 궁금합니다. ipconfig에 나오는 주소값도 자신의 ip주소를 가리키는 게 아닌가요?
-
미해결엑셀 매크로와 VBA 기초부터 실무활용까지 완전 정복
강의자료 깨짐
강의자료 다운받은게 매크로가 실행이 되지않습니다 (언어 설정이 깨져서 나와서 그런것같습니다) 해결방법이 있을까요? 그리고 오프라인에서 강의를 듣고싶은데 다운이 가능한지 궁금합니다
-
미해결React + GPT API로 AI회고록 서비스 개발 (원데이 클래스)
웹브라우저에서 글만작성하면 에러가 납니다
import { Input, Button} from 'antd'; const { TextArea } = Input; import { useState } from "react";// 저장하는 곳임포트 const DiaryInput = ({ isLoading, onSubmit }) => { const [userInput, setUserInput] = useState(""); // isLoading 로딩상태에서 사용하는 변수 // inSubmit 다입력 작성하면 사용 const handleUserInput = (e) => { setUserInput(e.target.value); }; const handleClick = () => { onSubmit(userInput); }; return ( <div> <TextArea value={userInput} onChange={handleUserInput} placeholder="오늘 일어난 일들을 간단히 적어주세요." /> <Button loading={isLoading} onClick={handleClick}> GPT 회고록을 작성해줘! </Button> </div> ); } export default DiaryInput; // import { Input , Button} from 'antd'; // import { useState } from 'react'; // const { TextArea } = Input; // const DiaryInput = ({isLoading, onSubmit}) => { // const [userInput, setUserInput] = useState(""); // //사용자의 입력을 받아 상위 컴포넌트로 넘기기 // // 로딩상태에서는 제출버튼 못누루게 // const handleUserInput =(e)=>{ // setUserInput(e.target.value); // const handleClick = ()=>{ // onSubmit(userInput); // } // } // return ( // <div> // <TextArea value={userInput} onChange={handleUserInput} placeholder='오늘 하루 회고'/> // <Button loading={isLoading} onClick={handleClick}>GPT회고록 시작</Button> // </div> // ); // }; // export default DiaryInput;import { useState } from 'react'; import { CallGPT } from './api/gpt'; import DiaryInput from './components/DiaryInput'; const dummyData = { "title": "고립된 개발자의 고민", "thumbnail": "https://source.unsplash.com/1600x900/?programming", "summary": "혼자 코딩과제를 진행하면서 걱정이다.", "emotional_content": "최근 혼자 코딩과제를 진행하면서, 협업이 없이 모든 것을 혼자 결정하고 해결해야 한다는 부담감에 많이 무겁습니다. 강의를 듣고 최선을 다해 프로젝트를 진행했지만, 예상치 못한 버그들로 인해 스트레스가 많이 쌓였습니다. 스택오버플로와 GPT를 통해 문제를 해결하긴 했지만, 이러한 문제해결 방식이 정말로 제 개발 실력을 향상시키는지에 대해 의문이 듭니다. 왠지 스스로의 능력을 시험할 기회를 잃은 것 같아 아쉽고, 불안감도 커지고 있습니다.", "emotional_result": "이 일기에서 감지되는 감정은 불안, 부담감, 그리고 자신감의 결여입니다. 고립된 상황에서의 성공에 대한 압박감과 문제 해결 방법에 대한 의심은 정서적으로 큰 부담을 주고 있습니다. 자기 효능감이 낮아짐을 느끼는 상황입니다.", "analysis": "고립되어 문제를 해결하는 과정은 큰 스트레스와 불안을 유발할 수 있습니다. '혼자서 하는 일은 좋은 일이든 나쁜 일이든 더욱 크게 느껴진다'는 에릭 에릭슨의 말처럼, 혼자서 모든 것을 해결하려는 시도는 때로는 개인의 성장에 도움이 될 수 있지만, 지속적인 고립은 자기 효능감을 저하시킬 수 있습니다. 이러한 상황에서는 자신의 노력을 인정하고, 필요한 경우 도움을 요청하는 것이 중요합니다.", "action_list": [ "프로젝트 중 발생하는 문제를 혼자 해결하려 하지 말고, 멘토나 동료 개발자와 상의를 통해 해결 방안을 모색하라.", "정기적으로 자신의 학습 방법과 진행 상황을 평가하여, 필요한 경우 학습 방식을 조정하라.", "개발 과정에서의 스트레스 관리를 위해 적절한 휴식과 여가 활동을 통해 정서적 안정을 찾으라." ] }; function App() { const [data, setData] = useState(dummyData); // 우선 빈문자열로 해놓고 const [isLoading, setIsLoading] = useState(false); const handleClickAPICall = async (userInput) => { try { setIsLoading(true);// 처음에는 로딩을 트루 const message = await CallGPT({ prompt: `${userInput}`, }); // Assuming callGPT is a function that fetches data from GPT API setData(JSON.parse(message)); } catch (error) { // Handle error (you might want to set some error state here) } finally { setIsLoading(false);//다음에는 펄스로 } }; const handleSubmit = (userInput) => { handleClickAPICall(userInput); }; console.log(">>data", data); return ( <> <DiaryInput isLoading={isLoading} onSubmit ={handleSubmit} /> <button onClick={handleClickAPICall}>GPT API call</button> <div>title : {data?.title}</div> <div>analysis : {data?.analysis}</div> <div>emotional_content : {data?.emotional_content}</div> <div>emotional_result : {data?.emotional_result}</div> </> ); }; export default App; // import { useState } from "react"; // import { CallGPT } from "./api/gpt"; // import { message } from "antd"; // import DiaryInput from "./components/DiaryInput"; // const dumyData = JSON.parse(` // { // "title": "당황스러운 예제 에러", // "thumbnail": "https://source.unsplash.com/1600x900/?confused", // "summary": "가끔 예제 에러가 발생하여 당황함", // "emotional_content": "가끔 예제 에러가 나타나는 것이 정말 당황스럽다. 이런 상황들은 예상치 못한 문제로 인해 나를 혼란스럽게 만든다. 그럼에도 불구하고, 이런 에러들은 동시에 나의 문제 해결 능력을 시험한다.", // "emotional_result": "당황스러움과 혼란스러움이 느껴진다. 그러나 이는 예상치 못한 문제에 대처하는 능력을 향상시키는 과정일 수 있다.", // "analysis": "당신의 당황함과 혼란스러움은 예상치 못한 상황에 대한 불안감과 두려움을 반영할 수 있습니다. 하지만, '문제는 기회다'라는 유명한 격언을 기억하십시오. 이러한 에러들은 당신의 문제 해결 능력을 향상시키는 좋은 기회일 수 있습니다.", // "action_list": [ // "예상치 못한 에러에 대비하는 습관 만들기", // "문제 해결 능력 향상을 위한 자기계발", // "당황하지 않고 차분하게 상황을 평가하는 능력 기르기" // ] // } // `); // function App() { // const [data, setData] = useState(dumyData); // const [isLoading, setIsLoading] = useState(false); // // 여기로딩상태가 // const handleClickAPICall = async (userInput) => { // try{// try catch로 감싸서, 처음에는 로딩상태를 트루라고 하고 // setIsLoading(true); // const message = await CallGPT({ // prompt:'{userInput}', // }); // setData(JSON.parse(message));// 그리고 데이터가 잘오면 받아보자 // } catch (error){ // }finally{ // setIsLoading(false);// 나중에는 false라고 하자 // } // }; // const handleSubmit = (userInput)=>{ // handleClickAPICall(userInput); // }; // console.log(">>data", data); // return ( // <> // <DiaryInput isLoading={isLoading} onSubmit={handleSubmit} /> // // 여기로 옴 // <button onClick={handleClickAPICall}>GPT API call</button> // <div>data : {data?.title}</div> // <div>thumbnail: {data?.thumbnail}</div> // <div>summary : {data?.summary}</div> // <div>emotional_resul : {data?.emotional_resul}</div> // <div>emotional_content : {data?.emotional_content}</div> // <div>analysis: {data?.analysis}</div> // <div>action_list: {data?.action_list}</div> // </> // ); // } // export default App;{ "name": "my-gpt-diary", "private": true, "version": "0.0.0", "type": "module", "scripts": { "dev": "vite", "build": "tsc -b && vite build", "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0", "preview": "vite preview" }, "dependencies": { "@ant-design/icons": "^5.4.0", "antd": "^5.20.1", "react": "^18.3.1", "react-dom": "^18.3.1", "styled-components": "^6.1.12" }, "devDependencies": { "@types/react": "^18.3.3", "@types/react-dom": "^18.3.0", "@typescript-eslint/eslint-plugin": "^7.15.0", "@typescript-eslint/parser": "^7.15.0", "@vitejs/plugin-react": "^4.3.1", "eslint": "^8.57.0", "eslint-plugin-react-hooks": "^4.6.2", "eslint-plugin-react-refresh": "^0.4.7", "typescript": "^5.2.2", "vite": "^5.3.4" } }
-
미해결실전! 스프링 부트와 JPA 활용1 - 웹 애플리케이션 개발
main 함수 실행 에러
첫번째 스크린샷 build ~ using을 인텔리제이로 썼을 땐 에러가 안 나는데 이번 강의에서 gradle(default)로 설정한 후 main함수 실행 시 에러가 뜨며 실행이 되지 않습니다. 다른 질문들 참고해봤는데 다른 건 없고 계속 똑같은 오류가 뜨더라구요.. 해결 방법이 있을까요?
-
미해결실무자를 위한 구글애널리틱스(GA4+GTM) 활용법(25년 Update)
수업 자료 공유 요청드립니다
한달 전 올라온 커뮤니티 글에 수업 자료 내용을 참고해서 커서를 아무리 옮겨보아도 수업 자료가 보이지 않습니다. 수업 자료를 다운 받을 수 있는 별도의 링크를 공유해주시길 부탁드립니다.
-
미해결[D.P.(DappProject)] 디앱 프로젝트(NFT 생성, NFT 구매 및 판매)
localhost 전환이 안됩니다.
터미널보면 문제 없는 것 같은데이 오류가 나면서 localhost로 접근이 안됩니다.원래 됐었는데 갑자기 안돼서 어떻게 해결해야하는지 모르겠습니다.개발자 도구보면 이런식으로 나옵니다 웹소켓 문제라고 하는데 캐시삭제해보고 remixd 삭제했다가 다시 설치해보고 브라우저를 바꿔봐도 여전히 안됩니다..
-
미해결
한글 깨짐
IDEA 콘솔창에서 한글이 깨집니다.커뮤니티 버전을 사용하고 있고, 기존의 QnA에서 보이는 것들 대부분 시험해봤는데 문제가 해결되기는 커녕 아예 서블릿 자체가 돌아가지 않는 등 더 악화되기만 해서 도로 원상복구시켰습니다. 이거 방법 없나요.
-
미해결[코드팩토리] [중급] Flutter 진짜 실전! 상태관리, 캐시관리, Code Generation, GoRouter, 인증로직 등 중수가 되기 위한 필수 스킬들!
styleFrom() 에서 primary 가 Deprecated 된 것
안녕하세요. 코팩님 초급 강의 듣다가 이제 중급으로 과감히 넘어온 수강생입니다 ! 첫번째 챕터를 하면서 styleFrom() 에서 막혔는데, 질문들 훑어 보고 한 번 해결해 봤는데 이대로 강의에 적용하면 되나요? ElevatedButton( onPressed: () {}, style: ElevatedButton.styleFrom( foregroundColor: PRIMARY_COLOR, ), child: Text('로그인'), ), TextButton( onPressed: () {}, style: TextButton.styleFrom( foregroundColor: Colors.black, ), child: Text('회원가입'), ),그리고, IOS랑 Android는 버튼 색감 자체가 차이가 있는 거기 때문에 색감 같은거는 앞으로 감안하면서 들으면 되는 건지요 ?? ㅎㅎ
-
미해결이득우의 언리얼 프로그래밍 Part2 - 언리얼 게임 프레임웍의 이해
10강 싱글톤 수업
싱글톤 수업을 보고 따라서 코드를 작성했는데 마지막에 라이브코딩을 하고난뒤에 결과물을 보니까 ui의 체력이 갑자기 반으로 줄어서 이상하다 했더니 캐릭터의 모든 수치가 0으로 되어있는데 이런경우는 어떤게 문제인지 아시나요? 혹시몰라서 선생님 코드와 비교해서 문제점은 찾아봤지만 다른건 찾지 못했습니다.
-
미해결평생 써먹는 데이터 기반 투자법 with 파이썬 퀀트 투자
강의 자료 다운로드 자료요청
안녕하세요.저도 강의자료를 다운로드하면 압축파일에 requirement.txt 파일만 나오고 다른 파일들은 보이지 않습니다.앞에서 문의한 분처럼 저도 이메일로 보내주시면 감사하겠습니다.kimv100@gmail.com감사합니다.
-
해결됨Readable Code: 읽기 좋은 코드를 작성하는 사고법
getter 질문드립니다
안녕하세요!예시에서 person.get지갑().get신분증().findAge() >= 19를 person.isAgeGreaterThanOrEqualTo(19) 메서드로 만들면person 내부에서 다시 지갑.get신분증().findAge() 형태가 되는데, 이 경우 지갑.isAge..(19) 같은 메서드를 계속 만드는지 끊어내는 기준이 있는지 궁금합니다.
-
미해결스프링 DB 1편 - 데이터 접근 핵심 원리
"정상 이체" 정상 실행인데 "이체중 예외 발생"은 실패하는 이유
학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.1. 강의 내용과 관련된 질문을 남겨주세요.2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.(자주 하는 질문 링크: https://bit.ly/3fX6ygx)3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예)[질문 내용]안녕하세요. 스프링 AOP는 스프링 컨테이너에서 등록된 빈들을 통해 DI가 되고 트랜잭션 프록시 객체를 생성하는 것은 완벽히 이해 했습니다. 근데 MemberServiceV3_3는 스프링 AOP를 쓰는데 강의처럼 Bean을 등록하기 전에 "정상 이체" 메소드는 정상 실행되고 "이체중 예외 발생"은 롤백이 일어나지 않아 실패하는건가요 ?빈들을 등록하지 않았기 때문에 "정상 이체" 메소드도 커밋이 되지 않아야 된다고 생각하는데 이유가 궁금합니다 !!
-
미해결Java 마이크로서비스(MSA) 프로젝트 실습
제목을 입력하지않았는데 포스트맨에서 제목이 나오지 않습니다.
package com.study.mstudy.item.controller;import com.study.mstudy.item.dto.ItemDTO;import com.study.mstudy.item.dto.ResponseDTO;import com.study.mstudy.item.service.ItemService;import jakarta.validation.Valid;import lombok.RequiredArgsConstructor;import lombok.extern.slf4j.Slf4j;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.http.ResponseEntity;import org.springframework.web.bind.annotation.*;@RestController@RequestMapping(value="v1/item")@Slf4j@RequiredArgsConstructorpublic class ItemController {private final ItemService itemService; @RequestMapping(value="/add",method= RequestMethod.POST)public ResponseEntity<ResponseDTO> add(@Valid @RequestBody ItemDTO itemDTO){ResponseDTO.ResponseDTOBuilder responseDTOBuilder = ResponseDTO.builder(); itemService.insertItem(itemDTO); log.debug("request add item id= {}",itemDTO.getId()); responseDTOBuilder.code("200").message("success"); return ResponseEntity.ok(responseDTOBuilder.build()); }}package com.study.mstudy.item.dto;import jakarta.validation.constraints.NotBlank;import jakarta.validation.constraints.Positive;import jakarta.validation.constraints.Size;import lombok.Data;@Datapublic class ItemDTO {@NotBlank(message = "ID는 필수 입력 값입니다.")@Size(max=10, message = "ID는 크기 10이하까지 작성가능합니다.")private String id; @Size(max=20, message = "이름은 20자까지 작성가능합니다.")private String name; @Size(max=200, message = "설명은 최대 200자까지 작성가능합니다.")private String description; @Positive private long count; private String regDts; private String updDts;}예제 보고 따라했으나..결과는 이미지 처럼 나오는데 저도 포스트맨으로설정하면 선생님처럼 나오게하고 싶은데 방법이 있을까요?
-
미해결[코드팩토리] [초급] NestJS REST API 백엔드 완전 정복 마스터 클래스 - NestJS Core
socket io database
안녕하세요 🙂 강의를 다 듣고 나서 ,ManyToMany 로 하지않고ManyToOne , OneToMany 로 중간테이블 생성을 했는데요그렇게해서 중간 테이블에 사용자가 언제 방에 들어왔는지 나갔는지를 체크하려고 했거든요만약 이렇게 할때 chats.gateway.ts 파일에 socket.join(data.chatIds.map((x) => x.toString()));이렇게해서 enter_chat 하는거 뿐만아니라데이터베이스에도 따로 save 를 해줘야하는거죠 ??