블로그
전체 8#카테고리
- 웹 개발
#태그
- JavaScript
- fetch
- axios
- 워밍업클럽
- 발자국
- FE
- 2주차
- 스터디
- 네트워크
- 1주차
- 과제
2024. 05. 17.
0
fetch와 axios 비교
웹 개발에서 데이터를 비동기적으로 가져오는 것은 매우 일반적인 작업이다. 이를 위해 주로 사용되는 두 가지 도구가 있는데, 바로 fetch와 axios이다. 참고로 이들은 구식 브라우저에서는 지원하지 않으므로 폴리필이 필요하다.Fetch 정의 :웹 브라우저 내장 API로, 네트워크 요청을 비동기적으로 처리하기 위해 만들어졌다. const res = await fetch(url); res.status; // response 코드 res.headers; // response 헤더 // response body await res.json(); // JSON 문자열을 파싱해서 자바스크립트 객체로 변환함. await res.text(); // 문자열을 그대로 가져옴.res.json() : 바디의 JSON 문자열을 파싱해서 자바스크립트 객체로 변환res.text() : 바디의 내용을 문자열로 그대로 가져옴.만약 body의 내용이 JSON이 아닌데 res.json으로 파싱하면 오류가 남. fetch() 옵션method (메소드)GET, POST, PATCH, DELETE지정하지 않으면 기본 값이 GETheaders (헤더)Content-TypeAuthorizationbody (바디)자바스크립트 객체는 그대로 전달할 수 없기 때문에 JSON 문자열로 바꿔줘야 함. 장점 :웹 표준:Fetch는 웹 표준으로, 모든 최신 브라우저에서 기본적으로 지원된다.웹 표준 API로서의 Fetch는 setTimeout, console 등과 함께 자주 사용된다. 단점 :추가 구현 필요:Fetch를 사용할 때는 axios와 비교하여 수동으로 구현해야 하는 기능들이 있다.예를 들어, 요청과 응답을 중간에 가로채어 처리하는 Interceptor 기능은 직접 작성해야 한다. // 요청을 보내기 전에 수행할 작업 const requestInterceptor = (url, options) => { console.log('Request Interceptor:', url, options); // 예: 인증 토큰 추가 const modifiedOptions = { ...options, headers: { ...options.headers, 'Authorization': 'Bearer YOUR_TOKEN' } }; return { url, options: modifiedOptions }; }; // 응답을 받은 후에 수행할 작업 const responseInterceptor = async (response) => { console.log('Response Interceptor:', response); if (!response.ok) { const errorData = await response.json(); throw new Error(`Error: ${response.status} - ${errorData.message}`); } return response.json(); }; const fetchWithInterceptors = async (url, options) => { const { url: interceptedUrl, options: interceptedOptions } = requestInterceptor(url, options); try { const response = await fetch(interceptedUrl, interceptedOptions); return await responseInterceptor(response); } catch (error) { // 에러 처리 console.error('Fetch Error:', error); throw error; } }; // 사용 예시 fetchWithInterceptors('https://api.example.com/data', { method: 'GET' }) .then(data => console.log('Data:', data)) .catch(error => console.error('Error:', error));응답값 파싱:Fetch는 기본적으로 응답값을 자동으로 파싱하지 않는다.응답을 JSON 형식으로 변환하려면 res.json() 메서드를 호출해야 한다. 이는 코드 작성 시 추가 단계를 필요로 한다.fetch('https://api.example.com/data') .then(response => response.json()) .then(data => console.log(data)) .catch(error => console.error('Error:', error));에러 핸들링: HTTP 오류 상태 코드(예: 404, 500)는 Fetch에서는 자동으로 에러로 처리되지 않는다.Fetch API에서는 HTTP 상태 코드가 200-299 범위가 아니어도 네트워크 요청이 성공하면 Promise를 반환한다. 따라서 상태 코드에 따라 별도로 오류를 처리해야한다. 이를 위해 res.status를 사용하여 각 상태 코드에 대한 처리를 세분화할 수 있다.export async function getColorSurvey(id) { const res = await fetch(`https://www./${id}`); if (!res.ok) { throw new Error('데이터를 불러오는데 실패했습니다.'); } const data = await res.json(); return data; }export async function getColorSurvey(id) { const res = await fetch(`https://www.example.com/${id}`); // 상태 코드에 따라 오류 메시지를 다르게 처리 if (!res.ok) { if (res.status >= 400 && res.status = 500) { throw new Error('서버 오류가 발생했습니다. 나중에 다시 시도하세요.'); } else { throw new Error('알 수 없는 오류가 발생했습니다.'); } } const data = await res.json(); return data; } axios 정의 :브라우저와 Node.js 환경 모두에서 동작하는 HTTP 클라이언트 라이브러리axios는 HTTP 메소드 이름과 동일한 메소드를 사용하고 리스폰스 바디를 data 프로퍼티로 접근할 수 있다. axios 옵션GET, DELETE RequestRequest body가 필요 없기 때문에 옵션을 두 번째 아규먼트로 받는다. POST, PATCH, PUTRequestRequest에 보낼 body 내용은 두 번째 아규먼트로 받고, 옵션을 세 번째 아규먼트로 받는다.별도의 파싱과정이 없이 JSON으로 변환된다. // Axios 모듈 가져오기 import axios from 'axios'; // GET 요청 (Request Body 없음) axios.get('https://api.example.com/data', { // 옵션 params: { id: 123 }, headers: { 'Authorization': 'Bearer token123' } }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); }); // DELETE 요청 (Request Body 없음) axios.delete('https://api.example.com/data/123', { // 옵션 headers: { 'Authorization': 'Bearer token123' } }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); });// POST 요청 (Request Body 있음) axios.post('https://api.example.com/data', { name: 'John Doe', age: 30 }, { // 옵션 headers: { 'Authorization': 'Bearer token123' } }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); }); // PATCH 요청 (Request Body 있음) axios.patch('https://api.example.com/data/123', { age: 31 }, { // 옵션 headers: { 'Authorization': 'Bearer token123' } }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); }); // PUT 요청 (Request Body 있음) axios.put('https://api.example.com/data/123', { name: 'Jane Doe', age: 25 }, { // 옵션 headers: { 'Authorization': 'Bearer token123' } }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); }); axios 인스턴스리퀘스트마다 공통되는 부분이 있으면 axios.create()으로 인스턴스를 생성한다.해당 인스턴스로 리퀘스트를 보내면 된다.const axios = require('axios'); // Axios 인스턴스 생성 const instance = axios.create({ baseURL: 'https://api.example.com/', // 기본 URL 설정 timeout: 5000, // 타임아웃 설정 (밀리초) headers: { 'Authorization': 'Bearer token123' // 기본 헤더 설정 } });// GET 요청 예제 instance.get('/data') .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); }); // POST 요청 예제 instance.post('/data', { name: 'John Doe', age: 30 }) .then(response => { console.log(response.data); }) .catch(error => { console.error('에러 발생:', error); });https://axios-http.com/docs/instance 참고 :Fetch() 함수는 원래 웹 브라우저에서만 사용할 수 있었으며, Node.js에서는 사용할 수 없었다.그러나 Node.js v17.5부터 실험적인 기능으로 Fetch가 도입되었고, 이에 따라 주의 메시지가 출력되었다.이후, Node.js v18.13부터는 이 기능이 안정화되어 더 이상 주의 메시지가 출력되지 않는다. 장점 :간편한 코드 작성 : 코드 작성이 간편하다.직관적인 문법 : 문법이 직관적이다.다양한 기능 : 인터셉터, 타임아웃, 요청 취소 등의 기능을 제공한다.에러 처리 용이 : catch 블록에서 에러 처리가 가능하다.자동 JSON 파싱 : 응답 데이터(res.data)는 자동으로 JSON으로 파싱된다.(텍스트로 파싱이 필요할 경우 res.text()를 사용하면 된다.)axios.get('https://api.example.com/data') .then(response => { console.log(response.data); // JSON 데이터, response.json() 불필요 }) .catch(error => { console.error('Error:', error); });단점 :번들 사이즈 증가 : axios는 많은 기능을 제공하지만 그만큼 번들 사이즈를 증가시킨다. 특히 번들 사이즈가 커지면 로딩 시간이 길어질 수 있다. axios의 기능 3개 :1) 인터셉터axios의 인터셉터는 요청과 응답을 가로채고 수정할 수 있는 기능이다. 이를 통해 전역적으로 요청과 응답을 처리하거나, 특정 상황에 맞게 헤더를 추가하거나 변경할 수 있다. 예를 들어, 모든 요청에 인증 토큰을 추가하거나, 응답 데이터를 특정 형식으로 변환하는 등의 작업을 수행할 수 있다. 모든 요청에 대해 인증 토큰 추가하기axios.interceptors.request.use(config => { const token = localStorage.getItem('token'); if (token) { config.headers.Authorization = `Bearer ${token}`; } return config; }, error => { return Promise.reject(error); }); 응답에 대한 에러 처리하기axios.interceptors.response.use(response => { // 응답이 성공인 경우 return response; }, error => { // 응답이 에러인 경우 if (error.response.status === 401) { // 인증 오류 처리 } else if (error.response.status === 404) { // 리소스를 찾을 수 없음 처리 } else { // 기타 오류 처리 } return Promise.reject(error); }); 요청 또는 응답에 대한 로깅axios.interceptors.request.use(config => { console.log('요청 시작:', config); return config; }); axios.interceptors.response.use(response => { console.log('응답 받음:', response); return response; }, error => { console.error('에러 발생:', error); return Promise.reject(error); }); 2) 타임아웃axios는 요청에 대한 응답을 기다리는 시간을 설정할 수 있는 타임아웃 기능을 제공한다.이를 사용하여 서버로의 요청에 대한 응답이 지연되는 경우, 일정 시간이 지난 후에 요청을 취소하고 에러를 발생시킬 수 있다.axios.get('/api/data', { timeout: 5000 }) .then(response => { // 성공적으로 데이터를 받았을 때의 처리 }) .catch(error => { // 타임아웃 또는 다른 에러 처리 }); 3) 요청 취소 기능axios는 요청을 취소하는 기능을 제공하여, 요청이 보내진 후에도 요청을 중단시킬 수 있다.이는 사용자가 요청을 취소하고 다른 작업을 수행할 때 유용하다.const source = axios.CancelToken.source(); axios.get('/api/data', { cancelToken: source.token }) .then(response => { // 성공적으로 데이터를 받았을 때의 처리 }) .catch(error => { if (axios.isCancel(error)) { // 요청이 취소된 경우 처리 } else { // 다른 에러 처리 } }); // 요청 취소 source.cancel('요청이 사용자에 의해 취소되었습니다.')
웹 개발
・
JavaScript
・
fetch
・
axios
2024. 05. 12.
0
인프런 워밍업 클럽 스터디 1기 FE | 2주차 발자국
목차React 세팅 Todo List 만들기 느낀점1. React 세팅Create-react-appnpm 또는 npx로 설치npm init react-app my-appnpx create-react-app my-appReact 애플리케이션을 만들기 위한 기본 파일 및 구조가 설정됨.npx 사용이 더 좋은 이유항상 최신 버전을 설치하므로 React를 설치한 후에도 다시 업데이트할 필요가 없음.프로젝트의 루트 디렉토리에 React를 설치하지 않고도 React 스크립트를 실행할 수 있음.프로젝트마다 React를 별도로 설치할 필요가 없음. 참고) 프로젝트 이름에 대문자 들어가면 오류 React 앱을 개발모드로 실행npm startsomething is already running on port 3000 에러Y를 누르면 다른 포트를 만들어서 동작하게 함. Vite 터미널에 해당 명령어를 입력해준다.npm create vite@latest프로젝트 이름을 지정해준다.Back-space 없이 그냥 입력하면 알아서 덮어 써진다.React를 선택한다.해당 명령어를 순서대로 입력하면 된다.SWC(Speedy Web Compiler)자바스크립트 프로젝트의 컴파일과 번들링 모두에 사용될 수 있는, Rust라는 언어로 제작된 빌드 툴말 그대로 매우 빠른 웹 컴파일러의 기능을 제공하는 툴 cd 입력하고 첫글자 누르고 tap 누르면 됨. 2. Todo List 만들기Todo List 만들 때 발생한 오류1) React에서 배열(리스트)를 렌더링할 때 각 항목에는 고유한 "key" prop이 있어야 함.해결 방법리스트로 렌더링되는 각 요소에 고유한 "key" prop을 추가하면 됨. 2) 요소에 value prop을 썼지만 해당 요소에는 onChange 핸들러가 없음.이런 경우 사용자 입력에 대한 처리가 없는 상태로 값을 변경할 수 없다고 경고 문구를 띄움.해결 방법1) defaultValue prop 사용2) onChange 핸들러 추가 this.setState({ value: e.target.value })} /> 3) TypeScript에서 이벤트 핸들러의 매개변수 타입은 일반적으로 React.ChangeEvent를 사용함. import React, { ChangeEvent } from "react"; handleChange = (e: ChangeEvent) => { console.log(e); };3. 느낀점이번 한 주 동안 기록할 만한 일이 없었다.채용 공고를 깔짝이면서 둘러보는 데 쓸데없이 시간을 낭비하였고, 아무것도 하기 싫다는 생각으로 퍼질러서 정말 별 것도 하지 않았다. 하지만 이제는 강의를 열심히 듣고 과제를 완성해야겠다는 생각이 들었다. 현재의 상황에 집중하고 최선을 다해야하는 것이 맞는 것 같다.
웹 개발
・
워밍업클럽
・
발자국
・
FE
・
2주차
2024. 05. 09.
0
웹, 웹 서버 및 WAS, SPA, SSR과 CSR, SSL/TLS
목차애플리케이션웹과 브라우저웹 표준서버와 클라이언트웹 서버와 웹 애플리케이션 서버 (WAS)Static Site GeneratorSingle Page Application (SPA)Server Side Rendering (SSR)와 Client Side Rendering (CSR)SSL(Secure Sockets Layer)과TLS(Transport Layer Security)TLS 핸드셰이크 애플리케이션운영체제(OS, Operating System) 위에 설치되어 운영체제의 도움을 받아 실행되는 응용 소프트웨어 웹과 브라우저웹(Web)World Wide Web의 줄임말인터넷을 통해 전 세계적으로 연결된 문서들의 집합을 의미함.이러한 웹 문서들은 HTML, CSS, JavaScript 등의 웹 기술로 작성되어 있음. 브라우저(Browser)웹을 사용자에게 표시해주는 소프트웨어브라우저는 사용자가 URL을 입력하거나 링크를 클릭하면 해당 웹페이지를 서버에서 가져와서 렌더링하고, 사용자가 읽을 수 있도록 화면에 표시함.사용자가 웹페이지와 상호작용할 수 있도록 링크를 클릭하거나 폼을 작성하는 등의 기능을 제공함.웹 개발자들이 작성한 코드를 서버로부터 받아오고, 그것을해석해서 모두가 이해할 수 있도록 시각화함.예) Google Chrome, Mozilla Firefox, Microsoft Edge, Apple Safari 등이렇게 웹과 브라우저는 매우 밀접한 관련이 있다. 웹 표준웹은 전 세계의 많은 사람들이 이용하기 때문에 사용자의 환경에 구애받지 않고 같은 내용을 보여주는 것이 중요함.이를 위해서 운영체제나 브라우저에 상관없이 웹 페이지의 내용을 일정하게 만들도록 하는 지침인 웹표준을 정해 웹 개발자들이 따르도록 해놓음. 서버와 클라이언트웹을 구성하는 주요 구성 요소 중 하나웹의 초기 형태는 정적인 웹 페이지를 제공하기 위한 서버-클라이언트 구조로 구상되었다.서버 : 웹 페이지를 저장하고, 클라이언트에게 요청에 따라 해당 페이지를 전송하는 역할을 수행클라이언트 : 웹 페이지를 요청하고 받아와서 웹 브라우저를 통해 표시함. 웹 서버와 웹 애플리케이션 서버 (WAS)WAS (Web Application Server) 등장 배경웹 페이지를 단순히 저장하고 제공하는 웹 서버가 개인화된 요구사항에 부합하기 어려운 상황(결제시스템, 쇼핑몰 등)에서, HTML을 동적으로 생성하고 사용자 요구에 따라 페이지를 구성하는 서버가 필요해졌음. 이를 웹 애플리케이션 서버(WAS)라고 함.WAS는 개인화된 요구사항을 충족시키기 위해 동적 콘텐츠 생성 및 제공, 데이터베이스와의 상호작용, 사용자 인증 및 세션 관리 등 다양한 기능을 수행함.이러한 기능 덕분에 WAS는 단순한 웹 서버와 구별되며, 사용자 요구에 맞게 동적으로 웹 페이지를 생성하고 제공할 수 있음.현재 WAS는 더 이상 단순히 웹 서버의 역할만을 수행하지 않고, 웹 서버의 기능까지 통합하여 더욱 효율적인 서비스를 제공함. 웹 서버와 웹 애플리케이션 서버 비교이미지 출처 : https://gmlwjd9405.github.io/2018/10/27/webserver-vs-was.html 웹 서버와 웹 애플리케이션 서버를 분리해야 하는 이유서버 부하 방지: 웹 애플리케이션 서버(WAS)와 웹 서버를 분리하여 서버 부하를 줄여야 함. WAS는 데이터베이스 조회 및 복잡한 로직 처리와 같은 작업에 집중하고, 간단한 정적 컨텐츠는 웹 서버에서 처리하는 것이 효율적임. WAS가 정적 컨텐츠까지 처리하면 서버 부하가 증가하고 응답 속도가 저하될 수 있음.보안 강화: SSL 암호화 및 복호화 처리를 위해 웹 서버를 활용할 수 있음. 웹 서버를 통해 SSL 인증서를 관리하고 암호화 트래픽을 처리하여 보안을 강화할 수 있음.여러 대의 WAS 연결 가능: 클라이언트의 요청을 여러 WAS로 분산하여 부하를 고르게 분배하고, WAS를 웹 서버로 연결함(로드밸런싱). 여러 대의 WAS를 연결하여 대용량 웹 어플리케이션을 운영하면서 무중단 운영과 장애 극복을 보다 효과적으로 처리할 수 있음.여러 웹 어플리케이션 서비스 가능: 하나의 서버에서 PHP, JAVA 등 다양한 언어의 애플리케이션을 함께 호스팅할 수 있음. 웹 서버를 통해 다양한 웹 어플리케이션을 효율적으로 관리하고 제공할 수 있음.→ 웹 서버를 WAS 앞에 배치하고 필요에 따라 웹 서버에 WAS를 플러그인 형태로 설정함으로써 효율적인 분산 처리를 할 수 있음.Static Site Generator정적인 사이트는 사용자의 요청에 따라 즉시 생성되는 것이 아니라, 미리 만들어진 페이지를 보여줌. 이를 위해 정적 사이트 생성기(static site generator)가 사용됨.정적 사이트 생성기는 웹 사이트의 구성 요소를 미리 만들고, 이를 템플릿화하여 고정된 형태의 페이지로 저장함. 이후에는 사용자의 요청에 따라 이러한 미리 생성된 페이지를 제공함.예: Jekyll (Ruby, GitHub Pages), Hugo (Go), Gatsby (React) 등 Server Side Rendering (SSR)SPA 등장 이전에 사용되던 방식으로, 서버에서 페이지를 요청할 때마다 완성된 페이지를 생성하여 보여주는 형식이를 통해 사용자가 해당 페이지에 접속할 때 완성된 페이지를 즉시 보여줌으로써 검색 엔진에서 사이트의 컨텐츠를 인식하는데 문제가 없음.최근에는 SPA에서도 SEO 문제를 해결하기 위해 SSR 방식을 지원하는 프론트엔드 프레임워크들(React, Vue, Angular 등 )이 등장함. Client Side Rendering (CSR)Ajax 등의 기술(XML HTTP Request), 자바스크립트 프레임워크를 활용하여, 데이터를 받아 자바스크립트로 페이지를 동적으로 만들 수 있게 됨.데이터는 XML, JSON 형태로 클라이언트에 전송. 이미지 출처 : https://velog.io/@namezin/CSR-SSR Single Page Application (SPA)기존에 페이지를 요청할 때마다 서버로부터 새로운 페이지를 받아와 보여주는 방식과는 달리, 페이지의 전체적인 렌더링이 한 번만 이루어지고 이후에는 필요한 데이터만 비동기적으로 요청하여 업데이트하는 방식임.SPA는 모바일 환경과 같이 통신 트래픽이 많고 성능이 낮은 환경에서 최적화되어 있음. 그러나 SPA에는 초기 로딩 시에 모든 페이지를 내려받아야 하기 때문에 초기 로딩 속도가 느린 단점이 있습니다.이를 개선하기 위해 Lazy Loading 방식이 도입됨. Lazy Loading은 SPA의 영역을 나누어 각 영역에 접근할 때 해당 페이지를 구성하도록 분리하는 방식임. 또한, SPA는 페이지 구성을 JavaScript로 동적으로 생성하기 때문에 검색 엔진 최적화(SEO)에 어려움을 겪을 수 있음. 이러한 문제를 해결하기 위해 Server Side Rendering (SSR)이 도입됨.SSR은 웹 사이트의 초기 로딩 시에 서버에서 페이지를 미리 렌더링하여 클라이언트에 전달함으로써 초기 구동 속도를 개선하고 SEO에도 더욱 유리한 환경을 제공함. SSG(Static Site Generation)CSR과 SSR의 단점들을 보완하기 위해 등장한 방식미리 서버에 화면을 저장해 두었다가 필요할 때 꺼내 사용하는 방식으로, 정적인 페이지를 생성하여 서비스함.초기 로딩 속도를 향상시키고 SEO(검색 엔진 최적화)를 개선할 수 있음. SSL과 TLSSSL보안 소켓 계층(Secure Sockets Layer, SSL)웹사이트와 브라우저 사이(또는 두 서버 사이)에 전송되는 데이터를 암호화하여 인터넷 연결을 보호하기 위한 표준 기술데이터를 암호화하여 보안을 강화하는 프로토콜로, 인터넷 통신에서 개인정보 보호와 데이터 무결성을 보장함.웹사이트의 URL에 "HTTPS"가 표시되는 것은 SSL/TLS를 사용하고 있음을 나타냄. TLS전송 계층 보안(Transport Layer Security)SSL의 후속 프로토콜로, SSL의 업데이트로 IETF에서 개발됨.HTTPS 작동의 근간을 이루는 TLS 핸드셰이크는 클라이언트와 서버 간의 인증 및 통신 보안을 담당함.TLS의 다양한 버전(TLS 1.0, 1.2, 1.3 등)은 보안 강화와 호환성을 위해 지속적으로 업데이트되고 있음. SSL/TLS 핸드셰이크TLS 핸드셰이크클라이언트와 서버 간의 통신을 안전하게 하는 인증 프로세스서로의 신원을 확인하고 암호화 알고리즘과 세션 키를 합의함.이를 통해 사용자의 개인 정보가 안전하게 전송되며, 특정 유형의 사이버 공격을 방지할 수 있음. TLS 핸드셰이크는 언제 발생할까?TLS 핸드셰이크는 사용자가 HTTPS를 통해 웹 사이트를 탐색하고 브라우저가 처음 해당 웹 사이트의 원본 서버를 쿼리하기 시작할 때마다 발생함.다른 통신이 API 호출 및 HTTPS를 통한 DNS 쿼리를 포함하는 HTTPS를 사용할 때에도 매번 TLS 핸드셰이크가 발생함.TLS 핸드셰이크는 TCP 연결이 TCP 핸드셰이크를 통해 열린 후에 발생함. 요약HTTPS는 HTTP 프로토콜 위에 SSL/TLS를 사용하여 보안을 강화한 것SSL은 데이터 통신을 보호하기 위한 암호화 프로토콜TLS는 SSL의 후속 프로토콜로, 이름이 바뀐 이유는 소유권 변경을 나타내기 위한 것이지 기능적 차이는 크게 없음.즉, HTTPS는 SSL/TLS를 사용하여 안전한 통신을 제공하는 웹 사이트를 지칭하는 용어참고 링크https://aws.amazon.com/ko/compare/the-difference-between-web-server-and-application-server/https://yozm.wishket.com/magazine/detail/1780/https://code-lab1.tistory.com/199https://www.cloudflare.com/ko-kr/learning/ssl/transport-layer-security-tls/https://velog.io/@namezin/CSR-SSRhttps://medium.com/@jayampathiadhikari/ssl-tls-simplified-c3c1f08051b2https://www.cloudflare.com/ko-kr/learning/ssl/what-happens-in-a-tls-handshake/https://www.digicert.com/kr/what-is-ssl-tls-and-https
웹 개발
・
스터디
・
네트워크
2024. 05. 05.
0
인프런 워밍업 클럽 스터디 1기 FE | 1주차 발자국
목차스터디 참가 계기와 소감 과제 내용앞으로의 방향1. 스터디 참가 계기와 소감 "'HTML, CSS, JS'로 나만의 웹사이트를 만들어 보아요!"라는 유혹적인 문구에 현혹되어 작년 말 웹 개발에 입문하게 되었다. 그리고 작년 크리스마스부터 개강한 모 KDT 국비교육 프론트엔드 부트캠프에 참가하게 되었고, 몇 주 전 수료를 하게 되었다. 4개월이 채 되지 않는 짧은 교육 기간에도 불구하고, 프론트엔드 개발자에게 필수적인 지식은 얼추 쌓을 수 있었다. 하지만 교육과정에서 진행된 두 개의 프로젝트에서 모두 백엔드를 담당하게 되면서 정작 프론트엔드 프로젝트가 하나도 없는 상태로 취업시장에 덩그러니 놓여지게 되었다. 백엔드 프로젝트 리팩토링이나 이력서 작성 등을 고민하며 시간을 낭비하고 있던 와중, 마침 인프런에서 진행하는 스터디를 발견하였다. 이 스터디에 참가하기 위해서는 무려 6만 6천원이라는 비용을 지불해야 했다. 강의 자체보다는 돈을 내고 스터디에 참여한다는 강제성이 큰 자극이 되어 꾸준한 학습을 진행하는 데 도움이 될 것이라고 판단하였다(강의가 수강료에 비해 좋지 않다는 의미가 절대 아니다). 실제로 기한이 주어지는 과제를 통해 평소라면 시작조차 하지 않았을 것들을 구현해보았다. 과제를 수행하면서 문제 정의와 해결 능력을 키울 수 있었다. 또한, 다른 참가자들이 꾸준히 참여하는 모습을 보는 것만으로도 자극을 받는다. 개발초보 취준생인 나부터 회사다니면서 공부하는 경력자분들, 그리고 공부하는 대학생분들까지 모두가 열심히 노력하는 모습을 보며 동기부여에 큰 도움이 되었다. 남은 기간 동안 목표 달성에 힘써야겠다.2. 과제 내용 1) 음식 메뉴https://www.inflearn.com/blogs/7678과제 설명 : 단골 카페인 쉬즈베이글의 메뉴를 만들어보았다. 카테고리별로 나누는 기능(필터링)을 구현하는 것이 핵심이었다.힘들었던 점 : 여태껏 쉬다가 오랜만에 바닐라 자바스크립트를 사용하려고 하니 그 자체가 버거웠다. 특히 자바스크립트로 HTML 요소들을 동적으로 생성하는 부분에서 많은 시간을 소모하였다.소감 : HTML 요소를 동적으로 생성하는 코드를 많이 작성하였다. 이게 효율적인지 의문이 들어서 시간날 때 연구를 해볼 것이다. 2) 가위바위보 게임https://www.inflearn.com/blogs/7768과제 설명 : 가위, 바위, 보 중 하나를 내면 게임이 진행된다. 각 회차별 남은 횟수 및 점수, 마지막 승부 결과와 리셋 버튼까지 구현해보았다.힘들었던 점 : 게임 로직은 단순하여도 여러 요소들을 화면에 렌더링하는 코드를 작성하는 것이 익숙하지 않아서 오래 걸렸다. 단순히 자바스크립트로 가위바위보 게임을 작성하라고 하면 쉬울텐데, 화면에 있는 여러 가지 요소들을 고려해야한다는 점에서 프론트엔드 개발이 쉽지 않다고 느낀다.소감 : Math.random을 활용하여 랜덤 생성하는 것이 어려워서 좀 연습을 해야할 것 같다. 3) 퀴즈(개발 진행중으로 링크 업로드하지 않음 ^^ >과제 설명 : 퀴즈 앱은 욕심을 많이 부려서 추가한 기능이 많기 때문에 아직 100% 완성하지는 못하였다. 현재 OX퀴즈에 있었던 큰 이슈를 해결한 상황이다.힘들었던 점 : 과제 중 이것이 가장 어려웠다. 일단 데이터를 불러와서 렌더링해야하는 점부터 어려웠고, 30문제의 데이터 중 10개를 뽑는 로직부터 작성하기 힘들었다. 다음 단계로 넘어갈 때 문제, 정답, 해설을 모두 업데이트 해야하는데, 오류가 매우 많아서 어떤 오류가 있었는지 기억이 잘 나지도 않는다.소감 : 처음부터 로직을 분리하여 추상화된 코드를 작성하고 싶은데 마음 같지 않다. 4) 책 목록https://www.inflearn.com/blogs/7759과제 설명 : 다른 이름의 투두리스트이다. 과제에는 삭제하는 것만 나온 것 같은데, 제대로 된 투두리스트를 만들어본 적이 없어서 수정, 삭제, 추가 기능 (임시저장, CSV 파일 변환, 전체 초기화)도 구현해 보았다.힘들었던 점 : html에서 태그를 처음 다루어보아서 낯설었고, CSV 파일 변환 기능 구현할 때 이슈가 많아서 별도로 정리해두었다.소감 : 일단 CRUD부터 정확하고 빠르게 구현한 후, 추가기능을 고도화하는 방향으로 진행해아 할 것 같다. 리액트도 CRUD부터 빠르고 정확하게 만드는 연습을 해야겠다. 5) 비밀번호 생성https://www.inflearn.com/blogs/7745과제 설명 : 최대 네 가지 조건을 만족하는 비밀번호를 생성하는 어플을 만드는 것이었다. 힘들었던 점 : 기본 아이디어는 네 가지 조건에 해당하는 문자열을 각각 변수에 담아두고, 해당 조건을 체크하면 문자열들을 합친 후 랜덤으로 인덱스를 생성하여 추출하는 방식으로 하였다. 그런데 이러한 경우 체크된 조건에 해당하는 문자가 하나도 없을 수 있기 때문에, 체크된 조건의 문자열은 무조건 무작위로 1개를 뽑은 후에 진행하는 로직으로 변경하였다. 이 부분이 어려웠다.소감 : 배열과 관련된 고차함수를 잘 다루는 것이 중요한 것 같다. 아직 많이 부족해서 꾸준히 공부하려고 한다. 전체 소감변수 선언시 const, let과 scope의 중요성을 명확하게 깨달았다. 이 부분과 관련해서 오류가 많이 났었다. 함수를 작성하더라도 반환값을 리턴하는 것을 간과하거나, 클래스를 생성할 때 constructor가 초기 실행 시점에 작동한다는 점 등 세부사항에 대한 고려가 필요함을 알게 되었다.코드를 작성하면서 로직을 분리하는 것이 얼마나 중요한지를 실감하게 되었다. 코드에 반복되는 패턴이 보인다면 이를 상위 수준으로 추상화하여 정리하는 것이 필요하다. 말은 쉽지만, 내 수준에서는 징그럽게 어렵다.GitHub Finder, 타이핑 테스트, 퀴즈 앱은 화요일까지 완성하려고 한다.3. 앞으로의 방향 1) 수료를 위한 필수적인 목표 바닐라 JS 과제 3개 (완료)리액트 과제 3개발자국 3회 작성 (매주 일요일) : - 발자국에 수업 내용도 정리하기 - 이번주는 수업 내용 정리를 못해서 다음주부터 진행할 예정그룹스터디 2회 참여 및 공부 내용 발표 2) 추가 목표 코드 리팩토링: 기능 개선 및 추가, CSS 적용 (특히 라이브러리 활용), 로직 분리 등을 통한 코드 개선배포 및 정리: 효울적인 코드 고민해보기
웹 개발
・
워밍업클럽
・
FE
・
발자국
・
1주차
2024. 05. 05.
0
인프런 워밍업 클럽 1기 FE 2번 과제 (가위바위보 게임 앱)
2번 과제 (Day2)(가위바위보 게임 앱)깃허브 저장소 주소 :https://github.com/devellybutton/frontEnd_warmingUp_study/tree/master/02.%EA%B0%80%EC%9C%84%EB%B0%94%EC%9C%84%EB%B3%B4 게임 규칙:사용자는 바위, 가위, 보 중 하나를 선택한다.컴퓨터는 무작위로 바위, 가위, 보 중 하나를 선택한다.사용자와 컴퓨터의 선택을 비교하여 승부를 결정한다.각 회차별 승부 결과와 점수는 화면에 표시된다.10회 진행 후 게임 종료. 최종 승부 결과와 재시작 버튼이 나타난다.재시작 버튼을 누르면 게임을 다시 시작할 수 있다. GIF:게임의 각 회차별 기록, 시작과 끝을 명확히 알 수 있도록 화면에 각 수치들을 렌더링 함. 가위바위보 버튼을 지나치게 빨리 누르는 것을 방지하기 위해 최소 0.5초에 1번씩 작동하도록 함. 간단한 후기 :간단한 로직이었기에 게임 자체는 금방 완성했지만, 예상보다 훨씬 많은 시간(^^)을 버그 수정에 투자해야 했습니다. 이 과정에서 코드의 중요성, 특히 로직 분리의 중요성을 절실히 깨달았습니다. 처음에는 모든 코드를 하나의 덩어리로 작성했기 때문에 버그를 찾기가 매우 어려웠습니다. 하지만 로직을 함수단위로 분리한 후에는 각 부분을 차근차근 검사하면서 문제를 해결할 수 있었습니다.특히, 게임 재시작 시 count가 2회씩 감소하는 문제는 이벤트 리스너가 중복 등록되어 발생하였습니다. 이 문제를 해결하기 위해 등록된 이벤트 리스너를 제거하고 로직을 분리하는 방식으로 코드를 수정했습니다. 아직 이벤트에 대해 깊게 공부해보지 못하였고, 다양한 이벤트를 사용해보지는 못해서 아쉽습니다.이번 과제를 통해 깔끔하고 체계적인 코드 작성의 중요성을 다시 한번 느꼈습니다. 이미지 출처 :https://www.vectorstock.com/royalty-free-vector/rock-paper-scissors-hand-gesture-vector-25169740개발할 때 참고한 링크 :https://oursmalljoy.com/css-%EC%9B%90-%EA%B7%B8%EB%A6%AC%EA%B8%B0-border-radius%EB%A1%9C-%EA%B0%84%EB%8B%A8%ED%9E%88-%EB%A7%8C%EB%93%A4-%EC%88%98-%EC%9E%88%EB%8B%A4/
웹 개발
・
워밍업클럽
・
FE
・
과제
2024. 05. 05.
0
인프런 워밍업 클럽 1기 FE 4번 과제 (책 리스트 나열 앱)
4번 과제 (Day4)(책 리스트 나열 앱)깃허브 저장소 주소 :https://github.com/devellybutton/frontEnd_warmingUp_study/tree/master/04.%EC%B1%85%EB%AA%A9%EB%A1%9D기능 :'책 이름', '책 저자', '읽은 날짜'를 입력하고 버튼을 누르면 표 아래에 하나씩 등록이 됨.각 항목별로 수정, 삭제가 가능함. (연필: 수정, 디스켓: 수정완료)CSV 파일로 저장 가능함. (화면 맨 오른쪽 첫 번째 아이콘)리스트 내 전체 내용 삭제 가능함. (화면 맨 오른쪽 두 번째 아이콘)LocalStorage에 임시저장하여 페이지 로딩시 불러옴. (화면 맨 오른쪽 세 번째 아이콘) GIF:'책 이름', '책 저자', '읽은 날짜'를 입력하고 버튼을 누르면 표 아래에 하나씩 등록이 됨.각 항목별로 수정, 삭제가 가능함.LocalStorage에 임시저장하여 페이지 로딩시 불러옴.CSV 파일로 저장 가능함.리스트 내 전체 내용 삭제 가능함. 간단한 후기 :4개월간의 프론트엔드 부트캠프를 마치며 저는 기본적인 기능 구현 능력을 갖추게 되었습니다. 하지만 부끄럽게도 제대로 된 투두리스트 하나를 완성하지 못한 채 수료를 하여 큰 부족함을 느꼈습니다. 그래서 수정, 삭제 및 추가 기능까지 구현해 보았습니다.필요한 기능만 간단하게 구현하는 것과, 모든 기능을 완벽하게 구현하는 것의 차이를 절실히 느꼈습니다. 기능 추가 및 고도화를 통해 예상치 못한 문제들과 부딪히면서, 개발 속도가 크게 저하되는 것을 이번에 절실히 경험했습니다. 물론 실력이 부족한 것도 이유가 될 것입니다.인터넷에 있는 소스가 정말 많은데, 단순히 정보를 검색하고 코드를 복사하는 것이 아니라 본인의 프로젝트 상황에 맞게 적용하는 것이 중요하다고 생각하였습니다.항상 부족한게 보이는 데 시간이 적어서 고민이 됩니다. 처음에 생각한 기능들은 다 구현하였으나, 아직까지 다음과 같은 문제가 있습니다.1) CSS가 제대로 적용되지 않음. 2) CSV 파싱할 때 콤마(,)를 기준으로 하여서 책 이름이나 저자에 콤마가 들어갈 경우 문제가 발생함. 3) 짝수번째 표(tbody의 td)의 맨 마지막열 CSS 배경 제거 필요함. 트러블슈팅 :굵직하게 3개의 문제점이 있었습니다. 이벤트 위임버튼을 클릭하여 행을 삭제하려면 클릭 이벤트를 추가하여 행을 삭제하는 함수를 호출해야 하였습니다.각 항목 생성 후, row.innerHTML을 사용하면 행이 삭제될 때 HTML이 완전히 새로 고쳐지므로 이벤트 리스너도 함께 삭제되어 제대로 적용이 되지 않는 문제가 있었습니다.이때 버튼의 상위 요소에 클릭 이벤트 리스너를 추가하고, 클릭된 버튼에 따라 수행처리를 하여 해결하였습니다.수정 전 (위) / 수정 후 (아래)if (deleteBtn) { deleteBtn.addEventListener("click", (e) => { e.preventDefault(); removeBook(e); }); } // 책 목록 개별 삭제 function removeBook(e) { const row = e.target.closest("tr"); if (row) row.remove(); }table.addEventListener("click", (e) => { if (e.target.id === "delete-btn") { e.preventDefault(); removeBook(e); } }); // 책 목록 개별 삭제 function removeBook(e) { const row = e.target.closest("tr"); // 하위에 있는 tr 선택하도록 함 if (row) row.remove(); } 클래스의 초기화 방법 수정ConvertToCSV 클래스의 getCSV 메소드에서 tbody와 thead에서 tr을 모두 찾아 반환되어야 하였습니다.하지만 초기에 페이지 로딩 시에는 tbody에 내용이 없어서 이 메소드를 사용하여 tr을 찾으면 tbody에 있는 내용이 없는 상태이기 때문에 정상적으로 작동하지 않았습니다.이에 따라 이 클래스의 constructor에서가 아닌 내부 메소드에서 tr을 찾도록 수정하였습니다. 브라우저에서는 tbody의 td가 있는 상태이므로 이 방법으로 문제가 해결되었습니다.CSV 파일 생성 시 한글만 깨지는 오류Blob 객체를 생성할 때 type에 charset=UTF-8을 넣어 주지 않아, 한글이 깨진 것이 아닌가 생각하였습니다.하지만 charset=UTF-8을 넣어도 같은 문제가 발생하여 [csv]를 ["\uFEFF" + csv]로 변경하니 해결되었습니다. csvFile = new Blob([csv], { type: "text/csv; charset=UTF-8" }); downloadLink = document.createElement("a"); downloadLink.download = filename; 이미지 출처 :https://www.flaticon.com/free-icon/download_9153957?term=download&page=1&position=16&origin=search&related_id=9153957https://www.flaticon.com/free-icon/restart_6532052?term=reset&page=1&position=18&origin=search&related_id=6532052https://www.flaticon.com/free-icon/bookmark_10238285?term=bookmark&page=2&position=38&origin=tag&related_id=10238285개발할 때 참고한 링크 :https://beomi.github.io/2017/11/29/HTML-Table-to-CSV/https://stackoverflow.com/questions/31959487/utf-8-encoding-issue-when-exporting-csv-file-in-javascript
웹 개발
・
워밍업클럽
・
FE
・
과제
2024. 05. 04.
0
인프런 워밍업 클럽 1기 FE 6번 과제 (비밀번호 생성 앱)
6번 과제 (Day6)(비밀번호 생성 앱)깃허브 저장소 주소 :https://github.com/devellybutton/frontEnd_warmingUp_study/tree/master/06.%EB%B9%84%EB%B0%80%EB%B2%88%ED%98%B8%EC%83%9D%EC%84%B1 과제 GIF:클릭한 종류의 문자열이 적어도 1개 이상 들어가도록 함. 모든 체크를 해제하고 'Generate'를 누르면 생성된 비밀번호가 초기화됨. 간단한 후기 :프론트엔드를 제대로 해본 적이 없어서 브라우저에서 클립보드를 조작하는 것을 처음 해보았습니다.구글 폰트 외에도 google material icon도 사용 가능하다는 것을 알게 되었습니다.이 정도 기능의 어플은 HTML 만들고 JS로 조작하는 것까지는 오래 걸리지 않지만, CSS까지 적용하니까 시간이 오래걸렸습니다. 항상 CSS가 문제인 것 같습니다.자바스크립트를 조작할 때는 각 옵션마다 적어도 1개 이상의 문자열이 랜덤으로 들어가야 하는 조건을 구현하는 것이 조금 까다로웠습니다. 처음에는 단순히 체크한 옵션의 문자열을 더해서 인덱스를 랜덤으로 생성되게 하였습니다. 하지만 그렇게 되면 선택한 옵션의 문자열이 들어가지 않는 경우가 발생해서(ex. 네 가지 다 선택하였음에도 Capital Letter는 하나도 들어가지 않은 경우) 로직을 변경하였습니다. 이미지 출처 :https://www.freepik.com/free-vector/padlock-security-safeguard-with-code-key-vector-locked-padlock-privacy-protect-tool-close-box-with-password-combination-system-lock-secure-equipment-template-realistic-3d-illustration_25191429.htm#query=lock%20png&position=7&from_view=keyword&track=ais&uuid=3024a5a2-6d85-4602-9058-ffaa8c44ee1dhttps://www.vecteezy.com/vector-art/23509276-gold-and-black-colors-bricks-wall-background-abstract-line-geometric-backdrop-minimal-design-style-stone-wall-texture-background-futuristic-art개발할 때 참고한 링크 :https://wooooooak.github.io/css%20challenge/2019/02/03/css_challenge_2/
웹 개발
・
워밍업클럽
・
FE
・
과제
2024. 04. 30.
0
인프런 워밍업 클럽 1기 FE 1번 과제 (음식 메뉴 앱)
1번 과제 (Day2) (음식 메뉴 앱)깃허브 저장소 주소 :https://github.com/devellybutton/frontEnd_warmingUp_study/tree/master/01.%EC%9D%8C%EC%8B%9D%EB%A9%94%EB%89%B4%EC%95%B1 과제 GIF: 간단한 후기 :자바스크립트를 사용해서 createMenuItem 함수로 HTML 요소를 생성하였습니다. fiterMenuItems 함수로 메뉴 행목을 필터링한 후, insertMenuItem 함수로 필터링된 항목을 DOM에 삽입하도록 하였습니다.이런식의 코드를 얼마 전 부트캠프의 1차 프로젝트에서 쓴 적이 있는데(이와 같이 자바스크립트로 html DOM을 생성하여 삽입), 이게 효율적인 방법인지는 잘 모르겠습니다. 안타깝게도 효율적인 방법이 떠오르지 않습니다. 해당 프로젝트에서 저는 백엔드 작업을 담당하였기 때문에, 프런트엔드 구현에 대한 고민은 깊게 하지 못했습니다.개인적으로 mock data만 넣으면 대충 만드는 경향이 있어서 단골카페에 있는 메뉴들을 직접 넣어보았습니다. 이미지 출처 :https://shesbagel.com/mainhttps://map.naver.com/p/search/%EC%89%AC%EC%A6%88%EB%B2%A0%EC%9D%B4%EA%B8%80/place/1834199837?c=15.00,0,0,0,dh&placePath=/home개발할 때 참고한 링크 :https://www.daleseo.com/css-object-fit/#google_vignettehttps://blog.naver.com/esc5411/221559783778https://velog.io/@rondido/Css-transform-scale
웹 개발
・
워밍업클럽
・
FE
・
과제