
주니어로서 반드시 필요한 건 아닐 수 있지만 이건 해야 경쟁력 가질 수 있음
굉장히 중요하다고 생각하는 부분. 그래도 못한다고 좌절할 필욘 x..
오늘 목차
1. refreshToken
2. graphql 원리
refreshToken
JWT는 항상 accessToken? X
accessToken은 항상 JWT? X
JWT는 DB에 로그인 정보를 저장하는 것의 대안으로 나온 방식
accessToken은 누가 중간에 탈취해갈 수 있어.
훈이가 철수꺼 탈취해서 나 철수요~ 하면서 철수의 jwt 토큰을 보냈어.
그럼 백엔드 입장에선 그게 누군지 몰라, jwt 복호화했더니 철수 나오니 철수!라고 생각해버림
그래서 accessToken 만료시간을 준다. 보통 30분~2시간으로 잡는다. (지금 (여기) 백엔드는 한 시간)
login 하면 JWT를 두 개 만들어, accessToken 30분~120분/refreshToken 2w~8w(2주~8주)
쿠키에 리프레쉬토큰 넣어서 보내준다. (document.cookie 접근 못하게 막아주는 httpOnly, secure 옵션 있음)
state엔 accessToken, cookie엔 refreshToken
(이건 자동으로 쿠키에 넣어준 것, 브라우저에 refreshToken은 자동으로 들어온다.)
accessToken은 우리가 recoil 통해 넣어줬고
필기 두 장 있습니다,,,
-----------------------------------여기에 필기 추가해줘...제발!!!@@!@!@!@!


만료된 토큰 가지고 요청 보내면 Browser는 UNAUTHENTED 에러를 반환한다.
-> UNAUTHENTED 에러면 refreshtoken을 가지고 accessToken 재발급 요청을 하게 한다.
그리고 그 후 새로 발급받은 accessToken을 state에 다시 담아준 후, 기존 요청에 실패했던 API를 다시 요청한다.
유저아갓시는 모르겠죠 ~
뒤에서 뭔 일이 일어나는지,,,
조용히 다시 로그인이 된 것. silent-auth라고 한다.
https 로만 접속 가능합니다. 아폴로 세팅에서 http -> https로 바꿔야 한다.
상품 등록하기를 눌렀다 치면, 한 번 눌렀을 때 이 세 과정이 이뤄지는 것
(onError 에러캐치, token 재발급, 실패 쿼리 재시도)
(로그인 유저 example 만료시간 5초, 10초)
refreshToken 실습

https!로 바꾸고, credentials: “include”, 추가
모든 api에 요청에 쿠키가 따라 붙는다.
accessToken이건 우리가 authorization에 직접 넣어준 거고 cookie <-이게 자동 첨부가 된다!
굳이 서버로 보내지 않아도 되는 데이터는 로컬스토리지에,
보안에 취약하다 하면 스테이트에,
매번 주고받고 해야한다 쿠키에~
import { onError } from '@apollo/client/link/error'
onError안에 graphQLErrors, operation(요청했던 API), forward 세 인자를 갖는 콜백 함수가 들어간다.
1. 만약 gql에러가 있다면
2. 에러를 하나씩 뽑아 해당 에러가 토큰 만료 에러(UNAUTHENTICATED)인지 확인해주고
3. 토큰 만료 에러라면 refreshToken으로 accessToken을 재발급 시켜주어야 하는데, 이 부분에서 ApolloClient세팅이 끝나지 않은 시점이기에 restoreAccessToken(useMutation)요청이 불가능했죠! 그렇기 때문에 우리는 graphql-request라이브러리를 사용하여 요청했습니다!
4. 재발급 받은 accessToken을 setAccessToken()을 통해 저장시켜주고,
5. 방금 실패한 쿼리의 정보가 담긴 operation의 설정을 operation.setContext({})를 활용해, accessToken만 변경하여 forword(operation)로 재요청
아폴로 세팅 밑에 있는 애들이 useMutation, useQuery.,.. 이런 거 쓸 수 있다.
아폴로 세팅 안에선 세팅 중인 것! 즉 지금 여기서 useMutation 쓸 수 없어.
어떻게 해?? -> 이럴 때 쓰는 라이브러리 : graphql-request
그래프 큐엘을 엑시오스처럼 사용할 수 있게끔 도와주는 도구 (아폴로 셋팅 없이)
yarn add graphql-request


Graphql의 진실~ 난,,, 사실...^^.............
아폴로 세팅 안 했는데 그래프큐엘 날릴 수 있어. 어째서??? (왜냐면 원래 rest-api거든)
Graphql - 페이스북이 만들었음
그 전엔 Rest-API
POST /boards - 게시글 등록
GET /boards - 게시글 목록 조회
사실 graphql은 endpoint가 /graphql인 POST방식의 REST-API다.
→ 수많은 endpoint 단일화,
→ 원하는 걸 묶어서 보내면서 해결할 수 있게 된 문제
한 화면에 패치 세 번 하고 싶어. axios 요청 세 번 해야 해. 근데 한 개씩밖에 못 가져와. 원하는 것보다 조금 가져와 ( underfetching )
결과물 일부만 가져오고 싶은데 다 가져와야해. 원하는 것보다 많이 가져와 ( overfetching )

setIsReply를 props로 내려서 props.setIsReply(false) 라고 썼는데 이게 계속 나옴...
댓글 작성과 대댓글 작성을 아예 분리할 생각이다. 설마 그러고도 나오려나?
다른 함수써도 이거 나오길래 보니까 아예 props로 내려주질 않은 듯...,, 그냥 나는 없는 함수를 쓴 거다..
알고리즘 : 모의고사
수포자는 수학을 포기한 사람의 준말입니다. 수포자 삼인방은 모의고사에 수학 문제를 전부 찍으려 합니다. 수포자는 1번 문제부터 마지막 문제까지 다음과 같이 찍습니다.
1번 수포자가 찍는 방식: 1, 2, 3, 4, 5, 1, 2, 3, 4, 5, ...
2번 수포자가 찍는 방식: 2, 1, 2, 3, 2, 4, 2, 5, 2, 1, 2, 3, 2, 4, 2, 5, ...
3번 수포자가 찍는 방식: 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, ...1번 문제부터 마지막 문제까지의 정답이 순서대로 들은 배열 answers가 주어졌을 때, 가장 많은 문제를 맞힌 사람이 누구인지 배열에 담아 return 하도록 solution 함수를 작성해주세요.
function solution(answers) {
let answer = [];
console.log(answers)
let a = [1,2,3,4,5];
let b = [2,1,2,3,2,4,2,5]
let c = [3,3,1,1,2,2,4,4,5,5]
// 인덱스와 값 둘 다 일치
console.log(a[0]===answers[0])
let a2 = [];
let b2 = [];
let c2 = [];
let aIdx = 0;
for(let i = 0; i < answers.length; ++i) {
if(a[i%a.length] === answers[i])
a2.push(answers[i]);
if(b[i%b.length] === answers[i])
b2.push(answers[i]);
if(c[i%c.length] === answers[i])
c2.push(answers[i]);
}
answer.push(a2.length);
answer.push(b2.length);
answer.push(c2.length);
answer.indexOf(Math.max(a2.length, b2.length, ...c2))
if(a2.length === b2.length & b2.length === c2.length) {
return [1,2,3]
}
}
solution([1,3,2,4,2,1,1,2,3,4]) // 1,2,3
못 풀었다. 가장 많이 맞춘 학생을 어떻게 ...? 넣어서 주지???에서 막혀서 못 풀었다.
1번 학생의 패턴 : 5개
2번 학생의 패턴 : 8개
3번 학생의 패턴 : 10개
문제 number % (패턴 수) 하면 몇 번 찍을지 알 수 있다.
const answerTable = [
// 1번 수포자가 찍는 방식
[1, 2, 3, 4, 5],
// 2번 수포자가 찍는 방식
[2, 1, 2, 3, 2, 4, 2, 5],
// 3번 수포자가 찍는 방식
[3, 3, 1, 1, 2, 2, 4, 4, 5, 5]
]
function solution(answers) {
// 학생들의 점수를 저장하는 배열
const score = [0, 0, 0];
let answer = [];
for(let i = 0 ; i<answers.length; ++i) {
for(let j = 0; j < answerTable.length; ++j) {
const answer = answerTable[j][i%answerTable[j].length];
if(answer === answers[i]) {
score[j]++;
}
}
}
// 제일 많이 맞춘 문제의 수를 뽑는다. 맞..힌..맞..춘
const biggest = Math.max(...score);
// 제일 많이 맞힌 학생의 번호를 오름차순으로 정렬해서 리턴한다.
for(let i = 0; i < score.length; ++i) {
if(biggest === score[i]) {
answer.push(i + 1);
} // sort 안해도 되는 이유, 이미 정렬 되어 있어서
}
return answer;
}
메서드 풀이
const answerTable = [
// 1번 수포자가 찍는 방식
[1, 2, 3, 4, 5],
// 2번 수포자가 찍는 방식
[2, 1, 2, 3, 2, 4, 2, 5],
// 3번 수포자가 찍는 방식
[3, 3, 1, 1, 2, 2, 4, 4, 5, 5]
]
function solution(answers) {
// 학생들의 점수를 저장하는 배열
const score = answerTable.map((el,i)=>{
const info = answers.reduce((acc,cur, j)=> {
console.log(cur, el[j%el.length]) // 와우 쩔어
return acc + (el[j%el.length]===cur ? 1 : 0)
// 정답이면 1 더하고 아니면 0 더하기
},0)
return { number: i+1, score: info };
})
const biggest = Math.max( ...score.map(el => {
return el.score;
}) );
console.log(biggest)
return score.filter(el=> {
return el.score === biggest;
}).map(el=> {
return el.number;
})
}
map에 대한 감 잡기 좋은 문제인 것 같다.

내가 풀던 방식 좀만 다듬으면 더 깔끔하게 풀 수 있지 않을까,,,!!!
오늘 알고리즘 문제는 풀지 못했다ㅠㅠ솔직히 조금만 더 노력했으면 풀었을 것 같은데, 알고리즘에 시간을 쏟는 게 점점 초조한 일이 되어가고있다... 이러면 안되는데! 대체 어떻게 해야할지 모르겠어! 정답은 없겠지만, 내가 틀린 건 아닐지 가끔 걱정하게 되는 요즈음...
그리고 블로그랑 일기 쓰는게 약간 벅찬 일이 되어가고 있다. 오늘은 블로그랑 일기가 밀려있어서 시간을 넉넉하게 잡고, 11시 30분쯤에 컴퓨터를 끈 것 같은데 이것저것 하다보니 또 12시가 넘었다... 이건 공부를 위해서라기보단 약간 기록에 대한 집착인 것 같다. 매일 일기를 쓰다보니까 진짜 습관이 되어버렸고, 기억 못하는 하루가 있는게 싫고 일기에 빵꾸나는 게 싫어서 뭐라도 적으려고 한다. 블로그도 접은 글에 이렇게 어쩌구저찌구 적다보니 + 이거 배운날 어땠더라? 궁금해질 때 봐야해서 평일만큼은 매일 적으려고 한다. 근데 문제는 하루씩 계속 밀린다는 것... 밀리니까 사진 찍어서 올려야할 필기도 헷갈리고,,, TIL, 알고리즘은 아예 학원에서 쓰면서 생활하는 게 좋겠다. 요즘 생활,,, 뭔가 우는 날도 있어야할 것 같고 몸도 엄청 피곤해야할 것 같은데, 물론 피곤은 한데... 생각보다 괜찮다. 아침에 졸린채로 만원버스 타고 학원가는 것도 조금 익숙해졌다. 아니 만원버스는 안 익숙할지도... 내일은 10분만 더 일찍 가보자!!! !!!!! 파이팅,, ^^,,,,, ,, , , ,
+ bean 멘토님이 정말 잘 가르쳐주신다고 느끼고 있는 요즘... 이걸 보시진 못하겠지만(보시면 안되지만,,^^) 정말 감사합니다.
오늘은 내게는 약간 특별한 날이어서, 그냥 6월 20일이라는 이유만으로 특별한 날이라서 평소보다 더 알차게 보내고 싶었다. 포트폴리오 하고 싶은 것도 많았는데, 못한게 많아서 아쉬웠다. 그래도 공부한다는 이유로 오늘을 그냥 넘길 순 없어서! 육회랑 맥주 먹었다. 30분의 행복^ㅅ^* 부트캠프 끝나면 꼭 가야지.




'프론트엔드✏️ > 코드캠프' 카테고리의 다른 글
220621 프론트엔드 부트캠프 42일차 : 이미지 업로드 최적화, promise-all, lazyload, preload (0) | 2022.06.21 |
---|---|
알고리즘 - 실패율, indexOf, lastIndexOf, 배열을 객체처럼! (0) | 2022.06.21 |
220619 프론트엔드 부트캠프 : 주말, 카카오맵 마커 변경 (0) | 2022.06.20 |
220617 프론트엔드 부트캠프 38일차: 카카오맵, SPA, MPA, callback-hell, promise, queue (0) | 2022.06.20 |
알고리즘 - 예산, JadenCase문자열 만들기 (0) | 2022.06.17 |