<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>엥</title>
    <link>https://brissy.tistory.com/</link>
    <description></description>
    <language>ko</language>
    <pubDate>Tue, 7 Apr 2026 22:33:24 +0900</pubDate>
    <generator>TISTORY</generator>
    <ttl>100</ttl>
    <managingEditor>에어팟맥스</managingEditor>
    <item>
      <title>리액트 useContext</title>
      <link>https://brissy.tistory.com/149</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;App.tsx 파일&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;import &quot;./App.css&quot;;
import { Header_X1 } from &quot;./x1_header/Header&quot;;
import { NavMenu } from &quot;./x1_header/NavMenu&quot;;
import { Login } from &quot;./main/login/Login&quot;;
import { BrowserRouter, Route, Routes } from &quot;react-router-dom&quot;;
import { HomeBody } from &quot;./main/home/HomeBody&quot;;
import { Register } from &quot;./main/register/Register&quot;;
import { MyPage } from &quot;./myPage/myPage&quot;;
import { MyPoint } from &quot;./myPage/MyPoint&quot;;
import { UserInfo } from &quot;./myPage/UserInfo&quot;;
import { DeleteAccount } from &quot;./myPage/DeleteAccount&quot;;

function App() {
&amp;nbsp;&amp;nbsp;return (
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;BrowserRouter&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Header_X1 /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;NavMenu /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Routes&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;/&quot; element={&amp;lt;HomeBody /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;/login&quot; element={&amp;lt;Login /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;/register&quot; element={&amp;lt;Register /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;/myPage&quot; element={&amp;lt;MyPage /&amp;gt;}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;point&quot; element={&amp;lt;MyPoint /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;userInfo&quot; element={&amp;lt;UserInfo /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Route path=&quot;deleteAccount&quot; element={&amp;lt;DeleteAccount /&amp;gt;} /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Route&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Routes&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/BrowserRouter&amp;gt;
&amp;nbsp;&amp;nbsp;);
}

export default App;&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;br&gt;페이지 구성은 위처럼 헤더, 메인메뉴가 공통으로 들어가있고 하단에 홈화면, 회원가입 화면, 로그인 화면, 마이페이지가 있다. 마이페이지에서는 포인트, 회원정보, 회원탈퇴 하위페이지가 있는 마이페이지 메뉴가 있다.&lt;br&gt;&amp;nbsp;&lt;br&gt;기능을 구현하면서 가장 고민을 했던 부분이 로그인 한 회원의 정보를 어떻게 저장하고 어디서부터 보내줘야(?) 할지 였는데&lt;br&gt;먼저 데이터베이스를 사용하지 않았기 때문에 전체 회원의 정보는 로컬스토리지에 userList 라는 키값으로 배열 형태로 저장이 되어있고, 로그인을 하면 로그인한 해당 회원의 고유 id 값을 세션스토리지에 저장을 해주도록 만들었다.&lt;br&gt;&amp;nbsp;&lt;br&gt;이때 세션에 저장된 id와 일치하는 회원을 로컬스토리지에서 찾아서 그 회원의 정보를 기억해두도록 하고싶었는데&lt;br&gt;처음에는 아래처럼 헤더에서 로그인한 사용자의 회원정보를 loginUserData에 담아서 Link의 state 에 담아서 하위 컴포넌트로 전달을 해주는 방법을 사용했다.&amp;nbsp;&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;&amp;lt;Link to=&quot;/myPage&quot; state={{ userData: loginUserData }}&amp;gt;&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;Link의 state를 사용하여 데이터를 전달하는 방식은 브라우저의 주소 창에 데이터를 노출시키지 않고 컴포넌트 간에 데이터를 전달할 수 있는 방법 중 하나이다. Link 컴포넌트를 사용하므로, 페이지 이동을 쉽게 구현할 수 있고, 전역&amp;nbsp;상태를&amp;nbsp;관리하는&amp;nbsp;Context&amp;nbsp;API나&amp;nbsp;Redux를&amp;nbsp;사용하지&amp;nbsp;않고도&amp;nbsp;컴포넌트&amp;nbsp;간&amp;nbsp;데이터&amp;nbsp;전달이&amp;nbsp;가능하다.&lt;br&gt;&amp;nbsp;&lt;br&gt;그런데 이 방법을 사용하면 데이터를 전역적으로 관리할 수 없기 때문에 해당 데이터를 전달받은 컴포넌트에서만 사용할 수 있고, URL이 변경되지 않기 때문에 브라우저의 앞뒤 버튼으로 페이지 이동이 불가능하기도 하고 브라우저의 주소창에는 정보가 노출되지 않아서, 북마크나 공유 기능이 제한된다는 단점이 있기 때문에 컴포넌트 간 데이터 전달은 단방향적으로만 이루어지므로, 복잡한 구조의 애플리케이션에서는 전역 상태를 관리하는 Context API나 Redux를 사용하는 것이 더 효율적일 수 있다.&lt;br&gt;&amp;nbsp;&lt;br&gt;현재 내가 만들고 있는 페이지는 복잡하지는 않지만 다른 기능들을 만들면서 여러가지 오류를 발견하기도 했고 다른 방법을 사용해보고 싶었다.&lt;br&gt;&amp;nbsp;&lt;br&gt;useContext는 React에서 제공하는 Hook 중 하나로, Context API를 사용하여 컴포넌트 간에 데이터를 공유할 수 있게 해준다. useContext 는 데이터를 전역적으로 관리하고 필요한 컴포넌트에서 가져와 사용하는 방식이다.&lt;br&gt;useContext를 사용하면 중간에 있는 부모 컴포넌트를 거치지 않고도 하위 컴포넌트끼리 데이터를 전달할 수 있기 때문에 데이터 전달이 간편하고 코드를 간결하게 작성할 수 있고, 중복되는 코드를 줄일 수 있다. 이는 특히 데이터를 다수의 컴포넌트에서 사용해야 할 때 유용하게 사용될 수 있다. 그리고 useContext를 사용하면 애플리케이션 전체에서 사용하는 데이터를 한 곳에서 중앙 집중적으로 관리할 수 있기 때문에 이를 통해 데이터를 쉽게 관리하고 유지보수할 수 있다는 장점이 있다.&lt;br&gt;&amp;nbsp;&lt;br&gt;그러나, useContext를 사용하여 전역적으로 데이터를 관리하면 해당 데이터를 관리하는 Context 객체를 생성해야 하므로 초기 설정과 추가 작업이 필요하다.&lt;br&gt;그러나 useContext를 사용하면 데이터를 가져오기 위해 매번 컴포넌트 트리를 순회해야 하기 때문에 컴포넌트 트리가 깊고 데이터를 자주 사용하는 경우에는 성능 이슈가 발생할 수 있다. 그리고 Context는 여러 컴포넌트에서 사용되기 때문에 데이터 변경이 예기치 않게 일어날 수 있고 예측하지 못한 오류를 발생시킬 수 있으며 데이터가 어디서 온 것인지를 파악하기가 어려워 질 수 있기 때문에 디버깅을 어렵게 만들 수 있다는 단점이 있다.&lt;br&gt;&amp;nbsp;&lt;br&gt;아직 리액트에 대해서 잘 이해하고 있지 못하기 때문에 어떤 방법을 사용하는게 좋을지 판단하기는 힘들지만 리액트의 여러가지 기능들을 사용해보고 싶어서 Link의 state를 사용해서 데이터를 넘겨주는 방식에서 useContext를 사용해서 헤더부터 데이터를 넘겨주는 방법으로 바꿔보았다.&amp;nbsp;&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;const loginUser =
&amp;nbsp;&amp;nbsp;sessionStorageController.getSessionStorage&amp;lt;FormDataType&amp;gt;(&quot;loginUser&quot;);

export const UserContext = createContext&amp;lt;FormDataType&amp;gt;(loginUser);&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;헤더에서 위처럼 UserContext 라는 context를 생성을 해 주었고,&amp;nbsp;&lt;br&gt;&amp;nbsp;&lt;br&gt;로그인 페이지에서&amp;nbsp;&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;const userContext = useContext&amp;lt;FormDataType&amp;gt;(UserContext);

useEffect(() =&amp;gt; {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (userContext.id) {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;navigate(&quot;/&quot;);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}
&amp;nbsp;&amp;nbsp;}, []);&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;이렇게 UserContext를 불러오니까 데이터가 잘 받아와졌다.&lt;br&gt;&amp;nbsp;&lt;br&gt;&amp;nbsp;&lt;br&gt;&amp;nbsp;&lt;br&gt;원래 context 를 사용할때는&amp;nbsp;&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;return (
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;AuthContext.Provider value={{ user, login, logout }}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{children}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/AuthContext.Provider&amp;gt;
&amp;nbsp;&amp;nbsp;);&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;이런식으로 Provider에서 생성한 context 값을 value로 전달해 주는 것이 일반적인 것 같은데 value 를 사용하지 않고도 context의 값을 참조할 수 있었다.&lt;br&gt;이유를 찾아보니까 value를 사용하지 않을 경우에는 Provider에서 생성한 context 값을 직접 참조하는데, 이때는 값을 변경할 수 없고, 단순히 읽기만 가능하다. 이런 방식은 단순한 상태를 전역적으로 사용할 때 유용하게 사용될 수 있다고 한다.&lt;br&gt;value를 사용할 경우에는 Provider에서 생성한 context 값을 value로 전달하고, value를 사용해 값을 변경할 수 있으며 보다 복잡한 상태를 전역적으로 사용할 때 유용하다고 한다.&lt;br&gt;&amp;nbsp;&lt;br&gt;일단은 시간이 부족해서 value를 사용하지 않고 데이터를 전달받기까지만 했지만 나중에 회원정보를 수정하는 기능을 구현하려면 value를 사용하고 데이터를 전달하도록 만들어야 할 것 같다.&lt;br&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>React</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/149</guid>
      <comments>https://brissy.tistory.com/149#entry149comment</comments>
      <pubDate>Tue, 9 May 2023 09:00:47 +0900</pubDate>
    </item>
    <item>
      <title>리액트로 회원가입 구현하기 - useRef vs useState</title>
      <link>https://brissy.tistory.com/148</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;전체 코드&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;import { Box, Button, Checkbox, CssBaseline, FormControlLabel, Grid, TextField, Typography, } from &quot;@mui/material&quot;;
import { Link, useNavigate } from &quot;react-router-dom&quot;;
import Container from &quot;@mui/material/Container&quot;;
import { useRef } from &quot;react&quot;;
import { LocalStorageController } from &quot;../../util/LocalStorageController&quot;;
import { FormDataType } from &quot;./type/FormDataType.type&quot;;
import React from &quot;react&quot;;

export const Register = () =&amp;gt; {
&amp;nbsp;&amp;nbsp;const navigate = useNavigate();

// is~~~Valid : input 값의 유효성을 검사하는 상태값. 
// 현재는 &quot;&quot;(빈칸)이 아니어야 통과를 할 수 있게 만들었지만 나중에 정규식을 넣어서 검사하도록 하려고 한다.
// 값이 false 이면 html 코드에서 error={!isUserNameValid}, helperText={isUserNameValid ? &quot;&quot; : &quot;필수 입력 항목입니다.&quot;}
// 로 경고창이 뜨게 된다.
&amp;nbsp;&amp;nbsp;const isUserNameValid = useRef(false);
&amp;nbsp;&amp;nbsp;const isUserIdValid = useRef(false);
&amp;nbsp;&amp;nbsp;const isPasswordValid = useRef(false);
&amp;nbsp;&amp;nbsp;const isPasswordCheckValid = useRef(false);

// input 의 value 값
&amp;nbsp;&amp;nbsp;const userName = useRef(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const userId = useRef(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const password = useRef(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const passwordCheck = useRef(&quot;&quot;);

&amp;nbsp;&amp;nbsp;const handleInputChange = (event: React.ChangeEvent&amp;lt;HTMLInputElement&amp;gt;) =&amp;gt; {
&amp;nbsp;&amp;nbsp;// input이 변할때마다 input의 name별로 value와 유효성 검사상태를 업데이트 해줌.
&amp;nbsp;&amp;nbsp;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;const { name, value } = event.target;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;switch (name) { 
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;case &quot;userName&quot;:
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userName.current = value;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isUserNameValid.current = Boolean(value);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;break;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;case &quot;userId&quot;:
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userId.current = value;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isUserIdValid.current = Boolean(value);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;break;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;case &quot;password&quot;:
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;password.current = value;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isPasswordValid.current = Boolean(value);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;break;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;case &quot;passwordCheck&quot;:
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;passwordCheck.current = value;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;break;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;default:
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;break;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}

// 비밀번호 input 입력창과 비밀번호 확인의 input 입력창의 value 가 같다면 true 반환
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (passwordCheck === password) {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isPasswordCheckValid.current = true;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;} else {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isPasswordCheckValid.current = false;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}
&amp;nbsp;&amp;nbsp;};

// 확인 버튼을 누르면 유효성을 체크하고 input의 입력값들(사용자 정보)을 로컬스토리지에 저장해주고
// 로그인 화면으로 이동시켜줌
&amp;nbsp;&amp;nbsp;const handleSubmit = (event: React.FormEvent&amp;lt;HTMLFormElement&amp;gt;) =&amp;gt; {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;event.preventDefault();

&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isUserNameValid &amp;amp;&amp;amp;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isUserIdValid &amp;amp;&amp;amp;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isPasswordValid &amp;amp;&amp;amp;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;isPasswordCheckValid
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;) {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;let n_id: number = 0;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;let point: string = &quot;50000&quot;;

&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;let userData: FormDataType = {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;id: n_id.toString(),
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userName: userName.current,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userId: userId.current,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;password: password.current,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userPoint: point,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;};

&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;let userList: FormDataType[] =
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;LocalStorageController.getLocalStorageList&amp;lt;FormDataType[]&amp;gt;(
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&quot;userList&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;) ?? [];

&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (userList.length &amp;gt; 0) {
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;n_id = parseInt(userList[userList.length - 1].id) + 1;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userData.id = n_id.toString();
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}

&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userList.push(userData);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;LocalStorageController.saveLocalStorage&amp;lt;FormDataType[]&amp;gt;(
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&quot;userList&quot;,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;userList
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;alert(&quot;회원가입이 완료되었습니다.&quot;);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;navigate(&quot;/login&quot;);
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}
&amp;nbsp;&amp;nbsp;};

&amp;nbsp;&amp;nbsp;return (
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Container component=&quot;main&quot; maxWidth=&quot;xs&quot;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;CssBaseline /&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Box
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;sx={{
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;marginTop: 22,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;display: &quot;flex&quot;,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;flexDirection: &quot;column&quot;,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;alignItems: &quot;center&quot;,
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Typography component=&quot;h1&quot; variant=&quot;h5&quot;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;회원가입
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Typography&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Box component=&quot;form&quot; noValidate onSubmit={handleSubmit} sx={{ mt: 3 }}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid container spacing={2}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={12}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;TextField
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;name=&quot;userName&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;required
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fullWidth
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;id=&quot;userName&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;label=&quot;성명&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;autoFocus
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;onChange={handleInputChange}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;error={!isUserNameValid}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;helperText={isUserNameValid ? &quot;&quot; : &quot;필수 입력 항목입니다.&quot;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;/&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={12} container spacing={2} alignItems=&quot;center&quot;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={9}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;TextField
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;required
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fullWidth
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;id=&quot;userId&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;label=&quot;아이디&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;name=&quot;userId&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;onChange={handleInputChange}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;error={!isUserIdValid}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;helperText={isUserIdValid ? &quot;&quot; : &quot;필수 입력 항목입니다.&quot;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;/&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={3}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Button variant=&quot;contained&quot;&amp;gt;중복확인&amp;lt;/Button&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={12}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;TextField
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;required
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fullWidth
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;name=&quot;password&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;label=&quot;비밀번호&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;type=&quot;password&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;id=&quot;password&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;onChange={handleInputChange}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;error={!isPasswordValid}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;helperText={isPasswordValid ? &quot;&quot; : &quot;필수 입력 항목입니다.&quot;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;/&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={12}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;TextField
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;required
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fullWidth
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;name=&quot;passwordCheck&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;label=&quot;비밀번호 확인&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;type=&quot;password&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;id=&quot;passwordCheck&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;onChange={handleInputChange}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;error={!isPasswordCheckValid}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;helperText={isPasswordCheckValid ? &quot;&quot; : &quot;필수 입력 항목입니다.&quot;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;/&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item xs={12}&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;FormControlLabel
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;control={&amp;lt;Checkbox value=&quot;allowExtraEmails&quot; color=&quot;primary&quot; /&amp;gt;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;label=&quot;약관 동의&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;/&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Button
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;type=&quot;submit&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;fullWidth
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;variant=&quot;contained&quot;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;sx={{ mt: 3, mb: 2 }}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;확인
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Button&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid container justifyContent=&quot;flex-end&quot;&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;Grid item&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&amp;lt;Link to=&quot;/login&quot;&amp;gt;이미 계정이 있다면?! 로그인 하러 가기&amp;lt;/Link&amp;gt;}
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Grid&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Box&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Box&amp;gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;lt;/Container&amp;gt;
&amp;nbsp;&amp;nbsp;);
};&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;html 코드는 Material UI 에서 제공하는 free template - sign up 사용(&lt;a href=&quot;https://mui.com/material-ui/getting-started/templates/&quot; target=&quot;_self&quot;&gt;&lt;span&gt;https://mui.com/material-ui/getting-started/templates/&lt;/span&gt;&lt;/a&gt;)&lt;/p&gt;&lt;hr data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style3&quot;&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;br&gt;useState와 useRef 는 모두 리액트에서 상태를 관리하는데 사용되는 Hook이다. 하지만 둘은 목적과 사용 방법에서 차이가 있다.&lt;br&gt;&amp;nbsp;&lt;/p&gt;&lt;h4 data-ke-size=&quot;size20&quot;&gt;useState()&lt;/h4&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- useState는 컴포넌트 내부에서 변화하는 값을 저장하고, 이 값을 변경할 때마다 컴포넌트를 리렌더링한다.&lt;br&gt;&amp;nbsp;- 상태를 변경할 때는 setState() 함수를 사용하며, 상태를 변경하면 해당 컴포넌트와 하위 컴포넌트가 모두 리렌더링된다.&amp;nbsp; &amp;nbsp;- 상태는 컴포넌트에서 변경되는 값이며, 다른 컴포넌트와 공유되지 않는다.&lt;br&gt;&amp;nbsp;&lt;/p&gt;&lt;h4 data-ke-size=&quot;size20&quot;&gt;useRef()&lt;/h4&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- useRef는 DOM 요소에 직접 접근하거나, 특정 값을 기억하고 싶을 때 사용된다.&lt;br&gt;&amp;nbsp;- useRef로 생성된 객체는 컴포넌트가 리렌더링되어도 계속 유지된다.&amp;nbsp;&lt;br&gt;&amp;nbsp;- useRef는 일반적으로 상태 변경에 따른 리렌더링과는 상관없이 동작하는 로직을 구현할 때 사용된다.&lt;br&gt;&amp;nbsp;&lt;/p&gt;&lt;h4 data-ke-size=&quot;size20&quot;&gt;useState와 useRef 의 차이점&lt;/h4&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- useState는 상태를 변경할 때마다 리렌더링이 발생하며, useRef는 상태 변경과 관계없이 계속 유지된다. &lt;br&gt;&amp;nbsp;- useState는 상태 값을 변경할 때마다 새로운 상태를 생성하는 반면 useRef는 기존에 생성된 객체를 계속 사용한다. &lt;br&gt;&amp;nbsp;- useState는 상태 값이 변경될 때마다 컴포넌트와 하위 컴포넌트가 모두 리렌더링되지만 useRef는 상태 변경과 관계없이 컴포넌트가 리렌더링되어도 기존 값을 유지한다. &lt;br&gt;&amp;nbsp;- useState는 컴포넌트 내에서 값을 저장하는 용도로 주로 사용되는 반면 useRef는 DOM 요소에 직접 접근하거나, 이전 값을 기억해야 하는 경우에 주로 사용된다.&lt;br&gt;&amp;nbsp;&lt;/p&gt;&lt;hr data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot;&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;br&gt;이 회원가입 기능을 구현하면서 처음에는 useState 로 아래처럼 초기값을 설정하고 사용했는데, 이렇게 하면 input 값이 바뀔 때마다 컴포넌트가 리렌더링이 된다.&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;&amp;nbsp;&amp;nbsp;const [isUserNameValid, setIsUserNameValid] = useState(false);
&amp;nbsp;&amp;nbsp;const [isUserIdValid, setIsUserIdValid] = useState(false);
&amp;nbsp;&amp;nbsp;const [isPasswordValid, setIsPasswordValid] = useState(false);
&amp;nbsp;&amp;nbsp;const [isPasswordCheckValid, setIsPasswordCheckValid] = useState(false);

&amp;nbsp;&amp;nbsp;const [userName, setUserName] = useState(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const [userId, setUserId] = useState(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const [password, setPassword] = useState(&quot;&quot;);
&amp;nbsp;&amp;nbsp;const [passwordCheck, setPasswordCheck] = useState(&quot;&quot;);&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;&lt;pre data-ke-type=&quot;codeblock&quot; class=&quot;typescript&quot; data-ke-language=&quot;typescript&quot;&gt;&lt;code&gt;export const Register = () =&amp;gt; {
	console.log(&quot;rerendering&quot;);&lt;/code&gt;&lt;/pre&gt;&lt;p data-ke-size=&quot;size16&quot;&gt;이렇게 콘솔로 찍어보면 useState를 사용했을 때는 input 값이 바뀔 때마다 콘솔창에 아래처럼 rerendering 이 계속 찍히는데( = 컴포넌트가 리렌더링 되고 있다는 것)&lt;/p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;375&quot; data-origin-height=&quot;305&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cqUuuh/btsejLCkYrv/kNB3eAilfkyhXkQKfXQlR0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cqUuuh/btsejLCkYrv/kNB3eAilfkyhXkQKfXQlR0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cqUuuh/btsejLCkYrv/kNB3eAilfkyhXkQKfXQlR0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcqUuuh%2FbtsejLCkYrv%2FkNB3eAilfkyhXkQKfXQlR0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;375&quot; height=&quot;305&quot; data-origin-width=&quot;375&quot; data-origin-height=&quot;305&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;br&gt;useRef 로 바꾸면 아래처럼 처음 렌더링 되었을 때만 콘솔창에 찍히고 input 에 값을 입력해도 아무것도 뜨지 않게 된다.&lt;/p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;420&quot; data-origin-height=&quot;245&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bzocxI/btsejLbimmC/TsyDG49ZVjkIGWZH6prVs0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bzocxI/btsejLbimmC/TsyDG49ZVjkIGWZH6prVs0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bzocxI/btsejLbimmC/TsyDG49ZVjkIGWZH6prVs0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbzocxI%2FbtsejLbimmC%2FTsyDG49ZVjkIGWZH6prVs0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;420&quot; height=&quot;245&quot; data-origin-width=&quot;420&quot; data-origin-height=&quot;245&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;br&gt;따라서 지금같은 회원가입창의 경우 input 값이 바뀔 때마다 리렌더링이 되는 것은 불필요하기 때문에 useState를 사용하지 않고 useRef 로 바꾸어 주었다.&lt;br&gt;&amp;nbsp;&lt;br&gt;지금처럼 작은 규모에서는 상관이 없겠지만 사이트의 규모가 커지게 되고, 컴포넌트 트리가 깊거나 복잡해지는 경우에는 불필요한 리렌더링이 발생하여 성능 저하의 원인이 될 수도 있다.&lt;br&gt;또한, 상태 값이 변경되어도 렌더링이 필요 없는 경우에도 리렌더링이 발생하여 낭비가 될 수 있다.&lt;br&gt;결론적으로 useState를 사용할 때에는 상태 값이 변경될 때 컴포넌트를 리렌더링해야 하는지에 대해 신중하게 고려해야 한다.&lt;br&gt;&amp;nbsp;&lt;br&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>React</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/148</guid>
      <comments>https://brissy.tistory.com/148#entry148comment</comments>
      <pubDate>Mon, 8 May 2023 14:37:41 +0900</pubDate>
    </item>
    <item>
      <title>도커와 가상머신</title>
      <link>https://brissy.tistory.com/147</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;- 도커란?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;도커란 어플리케이션을 패키징 할 수 있는 툴이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너라고 불리는 소프트웨어 유닛 안에 어플리케이션과 그에 필요한 시스템툴, 리소스들, 환경설정, 환경변수 등 모든 디펜던시를 하나로 묶어서 다른 서버, 다른 pc 등 어떤 곳에도 쉽게 배포하고 안정적으로 구동할 수 있게 도와주는 툴이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;한마디로 어플리케이션을 구동하는 데에 필요한 런타임 환경에 필요한 모든 것들을 어떤 pc 에서도 동일하게 구동할 수 있도록 도커 컨테이너 안에 담을 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;도커 - 컨테이너를 만들고, 배포하고, 구동한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너를 만들기 위해서는 세가지가 필요하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;먼저 도커파일을 만들어야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;어플리케이션을 구동하기 위해 꼭 필요한 파일들, 어떤 프레임워크나 라이브러리를 설치해야 하는지, 외부 디펜던시에 대해서 명시할 수 있고, 필요한 환경변수를 설정할 수 있고, 어떻게 구동해야 하는지 스크립트도 포함할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이렇게 작성한 도커파일을 이용해서 이미지를 만든다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이미지 안에는 어플리케이션을 실행하는 데에 필요한 코드, 런타임환경, 시스템 툴, 시스템 라이브러리, 모든 세팅들이 포함되어 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이렇게 만들어진 이미지는 변경이 불가능한 불변의 상태이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;객체지향에서 클래스의 개념과 비슷하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;마지막 단계인 컨테이너는 이미지를 고립된 환경에서 개별적인 파일 시스템 안에서 실행할 수 있는 것을 말한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너 안에서 어플리케이션이 동작한다고 보면 된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너에서 각각 동작하는 어플리케이션은 파일 생성, 수정 등 각각의 설정이 가능하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;각각의 컨테이너에서 수정된 파일들이 있어도 이미지에는 영향을 끼치지 않는다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너는 객체지향에서 인스턴스의 개념과 비슷하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;배포하기 - 로컬 머신(pc)에서 이미지를 생성해서 컨테이너 레지스트리(깃허브같은 개념)에 내가 만든 이미지를 푸시하고 필요한 서버나 다른 개발자 pc 에서 내가 만든 이미지를 가지고 와서 실행하면 된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정상적으로 실행하기 위해서는 그 pc 에 도커와 같은 컨테이너 엔진을 설치해두어야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 가상머신(vm)과 도커의 차이?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;가상머신은 하드웨이 인프라스트럭쳐 위에 vm웨어나 버츄얼박스같은 hyperviser 소프트웨어를 사용하여 각각의 가상머신을 만들 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;한 운영체제 위에서 어플리케이션을 각각의 고립된 다른 환경에서 구동하기 위해서 가상머신을 이용하여 구동해야 했다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;가상머신은 각각의 운영체제를 포함하고 있기 때문에 맥에서 vm 을 이용하면 윈도우와 리눅스를 동시에 구동할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이렇게 vm 을 사용하면 운영체제를 포함하고 있기 때문에 굉장히 무겁고 시작하는데도 오래걸리고 운영체제의 인프라스트럭쳐 리소스를 많이 잡아먹는다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;때문에 이 vm 에서 조금 경량화 된 컨셉이 container 이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너는 하드웨어에 설치된 운영체제(호스트 os) 에서 컨테이너 엔진이라는 소프트웨어를 설치만 하면 개별적인 컨테이너를 만들어서 각각의 어플리케이션을 고립된 환경에서 구동할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너는 운영체제를 포함하지 않고 컨테이너 엔진이 설치된 host os 를 공유하기 때문에 가볍다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;컨테이너가 구동되기 위해서는 컨테이너 엔진이 필요하고 엔진이 호스트os 에 접근해서 필요한 것들을 처리해준다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이 컨테이너 엔진중에 가장 많이 이용되는 것이 도커이다.&lt;/p&gt;</description>
      <category>기술 개념</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/147</guid>
      <comments>https://brissy.tistory.com/147#entry147comment</comments>
      <pubDate>Sun, 12 Mar 2023 17:33:31 +0900</pubDate>
    </item>
    <item>
      <title>객체와 클래스, 쿠키와 세션, 오버로딩과 오버라이딩, 싱글톤패턴, 접근제어자</title>
      <link>https://brissy.tistory.com/146</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;- 객체와 클래스의 차이&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;객체와 클래스는 객체 지향 프로그래밍(OOP)에서 중요한 개념이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;클래스는 객체를 만들기 위한 청사진(blueprint)이라고 볼 수 있다. 즉, 객체를 만들기 위한 필드와 메서드를 정의하는 일종의 틀이라고 생각할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;예를 들어, 자동차 클래스는 자동차 객체를 만들기 위한 필드와 메서드를 가지고 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;객체는 클래스의 인스턴스(instance)라고 볼 수 있다. 클래스를 바탕으로 실제로 만들어진 것이 객체이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;예를 들어, 자동차 클래스에서 만들어진 객체는 실제 자동차이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;객체는 클래스에서 정의한 필드와 메서드를 가지고 있으며, 필드는 객체의 상태(state)를 나타내고, 메서드는 객체의 동작(behavior)을 나타낸다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;따라서, 클래스는 객체를 만들기 위한 틀이고, 객체는 클래스를 바탕으로 실제로 만들어진 것입니다. 클래스는 여러 개의 객체를 만들기 위해 사용되며, 객체는 클래스에서 정의한 필드와 메서드를 가지고 있습니다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 쿠키와 세션의 차이&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;쿠키와 세션은 웹 개발에서 사용되는 기술로서, 사용자의 정보를 저장하고 유지하는 역할을 한다. 하지만 두 기술은 목적이나 사용 방법, 저장 위치 등에서 차이가 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;쿠키(Cookie)는 서버에서 생성하여 사용자의 웹 브라우저에 저장되는 작은 데이터 파일이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;쿠키를 사용하면 클라이언트에서 서버로 요청을 보낼 때, 해당 쿠키가 함께 전송된다. 즉, 쿠키는 클라이언트 측에서 저장되기 때문에 브라우저를 종료하고 다시 접속해도 유지된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;주로 로그인 상태 유지, 사용자 선호 설정 등을 저장하는 용도로 사용된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;세션(Session)은 서버에서 생성되는 정보 저장 공간으로, 세션은 서버에서 생성되어 클라이언트에게 고유한 세션 ID를 부여하며, 이 ID를 쿠키에 저장하여 브라우저에서 서버로 요청을 보낼 때 세션 ID를 전달한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이러한 방식으로 세션은 클라이언트 측에 저장되는 쿠키와는 달리 서버 측에서 관리된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;세션은 클라이언트가 브라우저를 종료하면 소멸되므로 보안이 중요한 정보를 저장하는 용도로 사용된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;요약하면, 쿠키는 클라이언트 측에서 저장되고, 브라우저를 종료하더라도 지속적으로 사용할 수 있지만 보안에 취약하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;세션은 서버 측에서 관리되고, 브라우저를 종료하면 삭제되지만 보안에 강력하다. 쿠키는 데이터 용량이 작고, 캐시와 같은 용도로 사용될 수도 있다. 세션은 데이터 용량이 크고, 로그인과 같은 인증과정에 사용될 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 오버로딩 오버라이딩 차이점&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;오버로딩(Overloading)과 오버라이딩(Overriding)은 객체지향 프로그래밍에서 다형성을 구현하는 방법 중 두 가지이다.&lt;/p&gt;
&lt;ol style=&quot;list-style-type: decimal; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;decimal&quot;&gt;
&lt;li&gt;오버로딩(Overloading)&lt;/li&gt;
&lt;/ol&gt;
&lt;ul style=&quot;list-style-type: disc; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;같은 이름의 메서드를 중복 정의하는 것을 의미한다.&lt;/li&gt;
&lt;li&gt;메서드 이름은 같지만 매개변수의 개수나 타입이 다르면 서로 다른 메서드로 인식한다.&lt;/li&gt;
&lt;li&gt;오버로딩된 메서드들은 컴파일러가 인자를 보고 어떤 메서드를 호출할지 결정한다.&lt;/li&gt;
&lt;/ul&gt;
&lt;ol style=&quot;list-style-type: decimal; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;decimal&quot;&gt;
&lt;li&gt;오버라이딩(Overriding)&lt;/li&gt;
&lt;/ol&gt;
&lt;ul style=&quot;list-style-type: disc; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;부모 클래스에 있는 메서드를 자식 클래스에서 재정의하는 것을 의미한다.&lt;/li&gt;
&lt;li&gt;메서드 이름, 매개변수의 개수, 타입, 반환 타입이 같아야한다.&lt;/li&gt;
&lt;li&gt;자식 클래스에서 오버라이딩된 메서드가 호출되면, 자식 클래스에서 재정의된 메서드가 호출된다.&lt;/li&gt;
&lt;/ul&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;즉, 오버로딩은 메서드 이름이 같지만 매개변수가 다른 경우에 사용하며, 오버라이딩은 상속 받은 메서드를 자식 클래스에서 재정의하여 사용하는 경우에 사용한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 싱글톤 패턴&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;싱글톤 패턴(Singleton Pattern)은 클래스의 인스턴스를 하나만 생성하고, 그 인스턴스에 대한 전역적인 접근을 제공하는 패턴이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;즉, 어떤 클래스의 객체를 단 한 개만 만들고 그 객체를 어디에서든지 참조할 수 있도록 하는 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;싱글톤 패턴을 구현하기 위해서는 해당 클래스의 생성자를 private으로 선언하고, 해당 클래스 내부에 유일한 인스턴스를 생성하고 외부에서는 그 인스턴스에 접근할 수 있는 public static 메서드를 제공하는 것이 일반적이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;싱글톤 패턴은 하나의 객체만을 사용하기 때문에 메모리 관리 측면에서 이점을 가질 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;또한, 전역 상태를 유지할 필요가 있는 경우나, 자원의 공유가 필요한 경우에 유용하게 사용될 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그러나, 싱글톤 패턴이 과도하게 사용될 경우, 의존성이 높아져 코드를 유지보수하기 어려워질 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 접근제어자(private, default, protected, public)&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;접근제어자(access modifier)는 클래스, 변수, 메소드 등의 멤버들에 대한 접근 권한을 설정하는 키워드이다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;b&gt;private&lt;/b&gt;: 해당 멤버는 같은 클래스 내에서만 접근 가능하다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;default&lt;/b&gt;(접근 제어자 생략 가능): 해당 멤버는 같은 패키지 내에서만 접근 가능하다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;protected&lt;/b&gt;: 해당 멤버는 같은 패키지 내에서 뿐만 아니라 상속받은 클래스에서도 접근 가능하다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;public&lt;/b&gt;: 해당 멤버는 어디서든 접근 가능하다.&lt;/li&gt;
&lt;/ul&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;각각의 접근 제어자는 다음과 같은 특징을 가지고 있다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc; color: #000000; text-align: start;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;b&gt;private&lt;/b&gt;: 클래스의 정보 은닉(캡슐화)을 위해 사용되며, 외부에서 함부로 접근하지 못하도록 한다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;default&lt;/b&gt;: 패키지 내에서만 접근 가능하므로, 같은 패키지에 속한 다른 클래스에서는 접근할 수 있지만, 다른 패키지에 속한 클래스에서는 접근할 수 없다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;protected&lt;/b&gt;: 상속과 관련하여 사용되며, 같은 패키지 내에서는 default와 동일하게 동작하지만, 다른 패키지에 속한 클래스에서도 상속받은 경우에는 접근할 수 있다.&lt;/li&gt;
&lt;li&gt;&lt;b&gt;public&lt;/b&gt;: 어디서든 접근 가능하므로, 모든 클래스에서 해당 멤버에 접근할 수 있다.&lt;/li&gt;
&lt;/ul&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;접근 제어자를 적절히 활용하여 정보 은닉과 데이터의 보안성을 높이고, 다른 클래스와의 상호작용을 제한하거나 허용할 수 있다.&lt;/p&gt;</description>
      <category>기술 개념</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/146</guid>
      <comments>https://brissy.tistory.com/146#entry146comment</comments>
      <pubDate>Sun, 12 Mar 2023 17:30:12 +0900</pubDate>
    </item>
    <item>
      <title>데이터베이스 개념</title>
      <link>https://brissy.tistory.com/145</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;- 데이터베이스 정규화란?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스의 정규화는 중복을 최소화하도록 설계하는 것이고, 비정규화는 읽는 시간을 최적화 하도록 설계하는 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스를 설계할 때 최소한의 데이터 중복, 최대한의 데이터 유연성을 위해 불필요한 데이터를 제거하고 중복을 최소화하여 데이터를 구조화하는 프로세스를 정규화라고 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정규화는 저장공간을 최소화 하고 데이터 구조의 안정성 및 무결성을 유지할 수 있지만, Relation의 분해로 인해 Relation 간의 연산(JOIN 연산)이 많아져서 질의에 대한 응답 시간이 느려질 수 있다는 단점이 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이를 극복하기 위해 부분적으로 비정규화를 사용하기도 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 비정규화는?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정규화된 엔티티, 속성, 관계를 시스템의 성능 향상 및 개발과 운영의 단순화를 위해 중복 통합, 분리 등을 수행하는 데이터 모델링 기법 중 하나이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;일반적으로 조회에 대한 처리 성능이 중요하다고 판단될 때 부분적으로 반정규화를 고려하게 된다. 디스크 I/O 량이 많거나, 테이블끼리의 경로가 너무 멀거나, 칼럼을 계산하여 조회할 때 성능의 저하가 우려될 때 반정규화를 고려하게 된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;항상 일정한 범위만을 조회하거나, 성능 상 이슈가 있거나, 테이블에 지나치게 조인을 많이 사용하게 되어 데이터를 조회하는 것이 기술적으로 어려울 경우 등이 반정규화의 고려 대상이 된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;단점은 반정규화를 과도하게 적용하다 보면 데이터의 무결성이 깨질 수 있고, 입력, 수정, 삭제의 질의문에 대한 응답 시간이 늦어질 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스의 정규화와 비정규화는 데이터베이스 설계에서 중요한 개념이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정규화는 데이터베이스의 테이블을 나누고 중복을 제거하여 데이터의 일관성과 무결성을 유지하는 과정이다. 일반적으로 정규화는 제1정규형, 제2정규형, 제3정규형 등 다양한 단계로 나뉘어 적용된다. 정규화를 통해 데이터 중복이 줄어들어 데이터 저장 공간을 절약하고, 데이터의 일관성과 무결성을 보장할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;반면 비정규화는 정규화된 테이블을 다시 하나의 테이블로 합치는 과정을 말한다. 이렇게 하면 데이터 조회 시에 조인 연산을 줄일 수 있기 때문에 성능 향상을 기대할 수 있다. 하지만 이렇게 데이터를 비정규화할 경우, 데이터 중복과 일관성 문제가 발생할 수 있으므로 신중하게 적용해야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;요약하자면, 정규화는 데이터의 일관성과 무결성을 유지하고 중복을 제거하여 저장 공간을 절약하는 반면, 비정규화는 성능 향상을 위해 중복을 허용하는 과정이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- Database 인덱스란?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스의 인덱스(Index)는 테이블에서 자주 검색되는 컬럼들의 값을 미리 정렬하여 검색 속도를 높이는 자료구조이다. 쉽게 말해, 인덱스는 데이터베이스에서 원하는 데이터를 빠르게 찾을 수 있도록 해주는 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;인덱스를 사용하면 검색 속도가 빨라지지만, 인덱스 자체도 데이터베이스의 용량을 차지하므로 인덱스를 사용할 컬럼을 선택하는 것이 중요하다. 또한, 인덱스를 사용하면 데이터의 삽입, 수정, 삭제 시에도 추가 작업이 필요하므로 인덱스를 너무 많이 사용하면 성능 저하가 발생할 수 있습니다. 따라서, 적절한 인덱스 설계가 필요하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스를 사용할 때 데이터의 양(row)에 따라 실행 결과의 속도가 차이가 나게 된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;특히 데이터의 양이 증가할수록 실행 속도는 느려지고, JOIN이나 서브 쿼리 사용 시 곱 연산이 일어나 데이터 양이 증가하기 때문에 WHERE 조건에서 필요한 데이터만 추출 후 사용하는 것이 좋다고 알고 있는데, 보다 쿼리의 성능을 높이는 데 중요한 것은 인덱스를 적재적소로 활용하는 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;특정 컬럼에 인덱스를 생성하면, 해당 컬럼의 데이터들을 정렬하여 별도의 메모리 공간에 데이터의 물리적 주소와 함께 저장한다. 만약 인덱스를 타게 되면 먼저 인덱스에 저장되어 있는 데이터의 물리적 주소로 가서 데이터를 가져오는 식으로 동작을 하여 검색 속도의 향상을 가져올 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;인덱스의 가장 큰 특징은 데이터들이 정렬이 되어있다는 점이다. 일반적으로 테이블을 만들고 안에 데이터가 쌓이게 되면 테이블의 행은 내부적으로 순서가 없이 뒤죽박죽으로 저장이 된다. 이렇게 되면 WHERE절에 특정 조건에 맞는 데이터들을 찾아낼 때도 레코드의 처음부터 끝까지 다 읽어서 검색 조건과 맞는지 비교하는 풀 스캔을 해야한다. 반면 인덱스 테이블을 스캔할 때는 데이터들이 정렬되어 저장되어 있기 때문에 해당 조건(WHERE)에 맞는 데이터들을 빠르게 찾아낼 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;단점은 인덱스를 관리하기 위해 추가 작업이 필요하다는 것이다. 항상 최신의 데이터를 정렬된 상태로 유지해야 원하는 값을 빠르게 탐색할 수 있는데, 데이터가 추가되거나 값이 변경되는 경우 인덱스 테이블 내에 있는 값들을 다시 정렬을 해야 한다. 인덱스 테이블, 원본 테이블 이렇게 두 군데의 데이터 수정 작업을 해줘야 한다. 따라서 INSERT, UPDATE, DELETE 의 DML 이 빈번하게 일어나는 테이블보다는 검색을 위주로 하는 테이블에 인덱스를 생성하는 것이 좋다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;또, 인덱스를 관리하기 위해서는 데이터베이스의 약 10%에 해당하는 저장공간이 추가로 필요하다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;인덱스가 쌓여가면서 전체적인 데이터베이스의 성능 저하를 초래할 수도 있기 때문에 인덱스는 최소한으로 사용하고 전체적인 sql 문을 효율적으로 짜는 방향으로 나아가야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 트랜잭션?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스의 트랜잭션(Transaction)은 데이터베이스에서 수행하는 작업의 단위를 의미한다. 하나의 트랜잭션은 하나 이상의 데이터베이스 작업들로 구성되며, 모든 작업이 성공적으로 수행되거나, 하나라도 실패할 경우 롤백(rollback)하여 이전 상태로 되돌리는 것을 보장한다. 이렇게 함으로써 데이터베이스의 일관성을 유지할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;트랜잭션은 &quot;원자성(Atomicity)&quot;, &quot;일관성(Consistency)&quot;, &quot;격리성(Isolation)&quot;, &quot;지속성(Durability)&quot;이라는 네 가지 속성을 가지고 있다. 즉, 하나의 트랜잭션은 완전한 하나의 작업으로 간주되며, 모든 작업이 성공적으로 수행되거나, 실패할 경우 이전 상태로 롤백된다. 이렇게 함으로써 데이터베이스의 일관성을 유지할 수 있다. 또한, 여러 개의 트랜잭션이 동시에 수행될 경우에도 각각 독립적으로 실행되는 것을 보장합니다. 마지막으로, 모든 성공적인 트랜잭션은 영구적으로 데이터베이스에 적용되는 것을 보장한다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 조인?&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스에서의 조인(join)은 두 개 이상의 테이블에서 가져온 데이터를 결합하여 하나의 결과 집합으로 반환하는 방법이다. 조인은 테이블 간에 연관된 데이터를 검색하는 데 사용된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;예를 들어, 고객 정보와 주문 정보가 있는 두 개의 테이블이 있다고 가정해보자. 고객 정보 테이블에는 고객의 이름, 주소, 전화번호 등이 포함되어 있고, 주문 정보 테이블에는 주문 번호, 주문 일자, 주문 수량 등이 포함되어 있다. 이 두 개의 테이블을 조인하면 고객이 어떤 주문을 했는지를 파악할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;조인의 종류에는 내부 조인(inner join), 외부 조인(outer join), 자연 조인(natural join) 등이 있으며, 각각의 조인은 다양한 상황에 따라 사용된다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;- 참조무결성&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;데이터베이스의 참조 무결성은 데이터베이스에서 관계형 데이터베이스를 구축할 때, 관계를 맺고 있는 두 테이블 사이에서 무결성을 보장하기 위한 것이다. 이를 위해 외래키(Foreign Key) 제약 조건을 사용한다. 외래키 제약 조건은 부모 테이블의 기본키(Primary Key)와 자식 테이블의 외래키(Foreign Key) 간의 관계를 정의하는 제약 조건이다.&lt;/p&gt;
&lt;p style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;외래키 제약 조건은 부모 테이블의 기본키를 참조하여 자식 테이블의 데이터를 제어한다. 즉, 부모 테이블의 기본키에 있는 값이 변경되거나 삭제되면, 해당 값을 참조하고 있는 자식 테이블의 데이터도 함께 변경이나 삭제되어야 한다. 이렇게 함으로써 데이터베이스의 데이터 일관성과 무결성을 유지할 수 있다.&lt;/p&gt;</description>
      <category>기술 개념</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/145</guid>
      <comments>https://brissy.tistory.com/145#entry145comment</comments>
      <pubDate>Sun, 12 Mar 2023 17:21:51 +0900</pubDate>
    </item>
    <item>
      <title>문제 해결 - 부트스트랩 모달 안보임</title>
      <link>https://brissy.tistory.com/144</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;예전에 쓰던 모달양식을 그대로 가져온건데 모달이 안보임&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1907&quot; data-origin-height=&quot;930&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/yPutl/btrRb8M86zx/S47za2pdPdHaVEHaqepAW1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/yPutl/btrRb8M86zx/S47za2pdPdHaVEHaqepAW1/img.png&quot; data-alt=&quot;모달창 띄우기 전 화면&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/yPutl/btrRb8M86zx/S47za2pdPdHaVEHaqepAW1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FyPutl%2FbtrRb8M86zx%2FS47za2pdPdHaVEHaqepAW1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;718&quot; height=&quot;350&quot; data-origin-width=&quot;1907&quot; data-origin-height=&quot;930&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;모달창 띄우기 전 화면&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1910&quot; data-origin-height=&quot;919&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/tHb0Y/btrQ6His2M8/oSbKYaa4nD8KaM41ErqCk1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/tHb0Y/btrQ6His2M8/oSbKYaa4nD8KaM41ErqCk1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/tHb0Y/btrQ6His2M8/oSbKYaa4nD8KaM41ErqCk1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FtHb0Y%2FbtrQ6His2M8%2FoSbKYaa4nD8KaM41ErqCk1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;721&quot; height=&quot;347&quot; data-origin-width=&quot;1910&quot; data-origin-height=&quot;919&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;모달 버튼을 클릭하면 화면에 스크롤이 없어지고 다른 곳이 클릭이 되지 않는 상태여서 부트스트랩이 적용이 되긴 한 것 같은데 화면은 그대로이고 모달창이 보이지 않았다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;702&quot; data-origin-height=&quot;194&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/52paU/btrRcQrBHV8/2HRVJl5CgBfwKfSqxtPl7K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/52paU/btrRcQrBHV8/2HRVJl5CgBfwKfSqxtPl7K/img.png&quot; data-alt=&quot;모달 html&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/52paU/btrRcQrBHV8/2HRVJl5CgBfwKfSqxtPl7K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F52paU%2FbtrRcQrBHV8%2F2HRVJl5CgBfwKfSqxtPl7K%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;593&quot; height=&quot;164&quot; data-origin-width=&quot;702&quot; data-origin-height=&quot;194&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;모달 html&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1197&quot; data-origin-height=&quot;45&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cemXqA/btrQ8HWOh2I/6BX2Qp8BFyuRwEcxsxBcQ0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cemXqA/btrQ8HWOh2I/6BX2Qp8BFyuRwEcxsxBcQ0/img.png&quot; data-alt=&quot;모달 버튼 html&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cemXqA/btrQ8HWOh2I/6BX2Qp8BFyuRwEcxsxBcQ0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcemXqA%2FbtrQ8HWOh2I%2F6BX2Qp8BFyuRwEcxsxBcQ0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;806&quot; height=&quot;30&quot; data-origin-width=&quot;1197&quot; data-origin-height=&quot;45&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;모달 버튼 html&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;547&quot; data-origin-height=&quot;246&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/syOam/btrQ4Xy5x1p/msGzEdkHod73ixPkkmH3ZK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/syOam/btrQ4Xy5x1p/msGzEdkHod73ixPkkmH3ZK/img.png&quot; data-alt=&quot;모달 css ( 오타 -&amp;amp;gt; .Modal 은 원래 .modal 임)&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/syOam/btrQ4Xy5x1p/msGzEdkHod73ixPkkmH3ZK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FsyOam%2FbtrQ4Xy5x1p%2FmsGzEdkHod73ixPkkmH3ZK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;418&quot; height=&quot;188&quot; data-origin-width=&quot;547&quot; data-origin-height=&quot;246&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;모달 css ( 오타 -&amp;gt; .Modal 은 원래 .modal 임)&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;잘 되던 모달을 그대로 복붙해온거라 코드에는 이상이 없는 것 같음&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;모달의 fade 는 모달을 감추었다가 보이게 할 때 사용하는 것으로 알고있는데 지금 내 경우에는 모달이 아예 감춰진 상태라 fade 부분에서 이상해졌나? 싶어서&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;해결 1단계&lt;/b&gt; - 모달 클래스에서 fade 를 삭제해봤다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;655&quot; data-origin-height=&quot;174&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bgYSzG/btrRbZo7TpM/RKBzg53xFLExJR8CKbX5nK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bgYSzG/btrRbZo7TpM/RKBzg53xFLExJR8CKbX5nK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bgYSzG/btrRbZo7TpM/RKBzg53xFLExJR8CKbX5nK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbgYSzG%2FbtrRbZo7TpM%2FRKBzg53xFLExJR8CKbX5nK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;520&quot; height=&quot;138&quot; data-origin-width=&quot;655&quot; data-origin-height=&quot;174&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1907&quot; data-origin-height=&quot;929&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/c1Lo16/btrQ6H3QZCk/W1gajeZyyZ7TLVdXDLGO2k/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/c1Lo16/btrQ6H3QZCk/W1gajeZyyZ7TLVdXDLGO2k/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/c1Lo16/btrQ6H3QZCk/W1gajeZyyZ7TLVdXDLGO2k/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fc1Lo16%2FbtrQ6H3QZCk%2FW1gajeZyyZ7TLVdXDLGO2k%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;704&quot; height=&quot;343&quot; data-origin-width=&quot;1907&quot; data-origin-height=&quot;929&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;모달창이 뜨긴 떴다.! 근데 좀 이상하긴 함&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;검색을 해 보니까 이상태에서 모달을 보이게 한 방법이 있어서 그대로 따라해봤다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(출처: &lt;a href=&quot;https://m.blog.naver.com/10hsb04/221672350510&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;https://m.blog.naver.com/10hsb04/221672350510&lt;/a&gt;)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;해결 2단계&lt;/b&gt; - 모달 클래스 css에 z-index: 1050 를 줘봤다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;685&quot; data-origin-height=&quot;240&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dxqL2I/btrQ8IBoq4F/ZUqHVSwO0SQqKq1Cj83q00/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dxqL2I/btrQ8IBoq4F/ZUqHVSwO0SQqKq1Cj83q00/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dxqL2I/btrQ8IBoq4F/ZUqHVSwO0SQqKq1Cj83q00/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdxqL2I%2FbtrQ8IBoq4F%2FZUqHVSwO0SQqKq1Cj83q00%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;539&quot; height=&quot;189&quot; data-origin-width=&quot;685&quot; data-origin-height=&quot;240&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1916&quot; data-origin-height=&quot;924&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bT74Mp/btrQ4aFtQ0t/6ukFimeRXKhFttpASkFPhK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bT74Mp/btrQ4aFtQ0t/6ukFimeRXKhFttpASkFPhK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bT74Mp/btrQ4aFtQ0t/6ukFimeRXKhFttpASkFPhK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbT74Mp%2FbtrQ4aFtQ0t%2F6ukFimeRXKhFttpASkFPhK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;758&quot; height=&quot;366&quot; data-origin-width=&quot;1916&quot; data-origin-height=&quot;924&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;모달 뜸 ! 문제 해결 완.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(z-index 의 1050 이라는 숫자는 의미가 있는 것 같다. 1050 이하의 숫자를 넣어보니 1단계 화면이랑 똑같이 안뜸)&lt;/p&gt;</description>
      <category>오류 해결</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/144</guid>
      <comments>https://brissy.tistory.com/144#entry144comment</comments>
      <pubDate>Mon, 14 Nov 2022 15:37:02 +0900</pubDate>
    </item>
    <item>
      <title>java.lang.ClassNotFoundException / 이클립스 clean 기능</title>
      <link>https://brissy.tistory.com/143</link>
      <description>&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;에러창.png&quot; data-origin-width=&quot;1257&quot; data-origin-height=&quot;562&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/kXWAS/btrMxTtqM6i/G2fxSNFwFQsA28JGcxJhw0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/kXWAS/btrMxTtqM6i/G2fxSNFwFQsA28JGcxJhw0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/kXWAS/btrMxTtqM6i/G2fxSNFwFQsA28JGcxJhw0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FkXWAS%2FbtrMxTtqM6i%2FG2fxSNFwFQsA28JGcxJhw0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1257&quot; height=&quot;562&quot; data-filename=&quot;에러창.png&quot; data-origin-width=&quot;1257&quot; data-origin-height=&quot;562&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;웹사이트 홈화면도 원래 잘 동작했었고, 홈화면 소스를 건드린 곳이 없는데 갑자기 안돌아가고&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;코드를 자세히 뜯어봐도 틀린게 없어보이는데&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아니 무엇보다 클래스가 떡하니 있는데 왜 매핑된 클래스가 없다고 뜨는거임..????? 왜?????&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;java.lang.ClassNotFoundException 에러가 뜨면서 작동이 안되는게 이상해서 구글링을 해보다가&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span&gt;java.lang.ClassNotFoundException&lt;span&gt; 에러가 나타날 때는&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;상단바에 project 메뉴에 있는 clean 을 해보면 작동이 될 수도 있다고 해서 해보았다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;프로젝트클린.png&quot; data-origin-width=&quot;293&quot; data-origin-height=&quot;313&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/tVSoJ/btrMw5uv9St/3kqR45D20zsmVTeNWbNcNk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/tVSoJ/btrMw5uv9St/3kqR45D20zsmVTeNWbNcNk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/tVSoJ/btrMw5uv9St/3kqR45D20zsmVTeNWbNcNk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FtVSoJ%2FbtrMw5uv9St%2F3kqR45D20zsmVTeNWbNcNk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;248&quot; height=&quot;313&quot; data-filename=&quot;프로젝트클린.png&quot; data-origin-width=&quot;293&quot; data-origin-height=&quot;313&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;클린.png&quot; data-origin-width=&quot;567&quot; data-origin-height=&quot;523&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/vIkes/btrMtFpqwIW/vbBKb6MNBtBSSfFNq1bGu0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/vIkes/btrMtFpqwIW/vbBKb6MNBtBSSfFNq1bGu0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/vIkes/btrMtFpqwIW/vbBKb6MNBtBSSfFNq1bGu0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FvIkes%2FbtrMtFpqwIW%2FvbBKb6MNBtBSSfFNq1bGu0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;458&quot; height=&quot;523&quot; data-filename=&quot;클린.png&quot; data-origin-width=&quot;567&quot; data-origin-height=&quot;523&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 다시 코드를 실행시켜보니까 ....!&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;화면 캡처 2022-09-19 120326.png&quot; data-origin-width=&quot;1112&quot; data-origin-height=&quot;352&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/440Pu/btrMrT2CIvI/Zk6iiKkUPCyBAwLBklsNSk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/440Pu/btrMrT2CIvI/Zk6iiKkUPCyBAwLBklsNSk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/440Pu/btrMrT2CIvI/Zk6iiKkUPCyBAwLBklsNSk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F440Pu%2FbtrMrT2CIvI%2FZk6iiKkUPCyBAwLBklsNSk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1112&quot; height=&quot;352&quot; data-filename=&quot;화면 캡처 2022-09-19 120326.png&quot; data-origin-width=&quot;1112&quot; data-origin-height=&quot;352&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;잘 돌아간다. 어이없음. 역시 내가 틀린게 아니었어&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;project 의 clean 기능은&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;있는 파일들을 지우는게 아니라&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이클립스가 사용하고 있던 (기억하고 있는?) 정보나 클래스 등의 파일들을 깔끔하게 정리하고&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;다시 만드는 개념이라고 한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;주로 빌드가 꼬였을 때 다시 정리하는 용도로 사용된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style3&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;+++++ 추가 +++++&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그 뒤로도 계속 clean 을 눌러줘야 변경사항이 인식되는 문제로 너무 귀찮았는데,&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;알고보니 저 Build Automatically 가 체크가 안되어있어서 그랬던 거였다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;내가 실수로 체크해제를 했었나보다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;다시 체크해주니까 변경사항도 자동으로 인식이 잘 됨 ㅎ&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;307&quot; data-origin-height=&quot;298&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bpq43a/btrMUShw69f/6R5O5xF8oY68HlHUr57kR0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bpq43a/btrMUShw69f/6R5O5xF8oY68HlHUr57kR0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bpq43a/btrMUShw69f/6R5O5xF8oY68HlHUr57kR0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fbpq43a%2FbtrMUShw69f%2F6R5O5xF8oY68HlHUr57kR0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;307&quot; height=&quot;298&quot; data-origin-width=&quot;307&quot; data-origin-height=&quot;298&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;</description>
      <category>오류 해결</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/143</guid>
      <comments>https://brissy.tistory.com/143#entry143comment</comments>
      <pubDate>Tue, 20 Sep 2022 00:26:59 +0900</pubDate>
    </item>
    <item>
      <title>HTTP 요청 헤더를 파싱하는 중 오류 발생 / java.lang.IllegalArgumentException / HTTP 상태 400 - 잘못된 요청</title>
      <link>https://brissy.tistory.com/142</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style3&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;lt;목표&amp;gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;웹페이지에서 비밀번호 찾기를 누르면 나오는 모달창에서&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. 아이디와 이메일을 입력받고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 입력받은 이메일로 인증코드를 보낸 다음,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. 전송받은 인증코드를 입력하면&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;4. 새 비밀번호를 입력받아서&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;5. 비밀번호를 새로 만든다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이때, 인증코드를 잘못 입력하면 아이디와 이메일을 입력받는 초기창으로 돌아감.&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;lt;문제 발생&amp;gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;인증코드 전송까지는 잘 되는데 &lt;b&gt;올바른 인증코드를 입력하면&lt;/b&gt; 아래 사진처럼 &lt;b&gt;오류가 발생&lt;/b&gt;한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(틀린 인증코드를 입력하면 정상작동됨.)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;621&quot; data-origin-height=&quot;660&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/PKAoX/btrMhWqyUZ7/Wk0W8PmPNDic81DGWd2K70/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/PKAoX/btrMhWqyUZ7/Wk0W8PmPNDic81DGWd2K70/img.png&quot; data-alt=&quot;웹페이지 에러창&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/PKAoX/btrMhWqyUZ7/Wk0W8PmPNDic81DGWd2K70/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FPKAoX%2FbtrMhWqyUZ7%2FWk0W8PmPNDic81DGWd2K70%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;354&quot; height=&quot;660&quot; data-origin-width=&quot;621&quot; data-origin-height=&quot;660&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;웹페이지 에러창&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1512&quot; data-origin-height=&quot;695&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/nIreC/btrMi6MIIg0/93W2FR3kJNfW1yG0xkaMTk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/nIreC/btrMi6MIIg0/93W2FR3kJNfW1yG0xkaMTk/img.png&quot; data-alt=&quot;콘솔창 에러메시지&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/nIreC/btrMi6MIIg0/93W2FR3kJNfW1yG0xkaMTk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FnIreC%2FbtrMi6MIIg0%2F93W2FR3kJNfW1yG0xkaMTk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1512&quot; height=&quot;695&quot; data-origin-width=&quot;1512&quot; data-origin-height=&quot;695&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;콘솔창 에러메시지&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;837&quot; data-origin-height=&quot;364&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bLaBqA/btrMhDrhnFo/621vkzvVRMXX3ngkk4Jlo0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bLaBqA/btrMhDrhnFo/621vkzvVRMXX3ngkk4Jlo0/img.png&quot; data-alt=&quot;F12 콘솔창 에러메시지&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bLaBqA/btrMhDrhnFo/621vkzvVRMXX3ngkk4Jlo0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbLaBqA%2FbtrMhDrhnFo%2F621vkzvVRMXX3ngkk4Jlo0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;722&quot; height=&quot;314&quot; data-origin-width=&quot;837&quot; data-origin-height=&quot;364&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;F12 콘솔창 에러메시지&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;lt;오류 해결 과정&amp;gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;콘솔창 에러메시지 마지막 줄인&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #ef6f53;&quot;&gt;&lt;span style=&quot;color: #000000;&quot;&gt;1.&lt;/span&gt; &lt;b&gt;pwdUpdateEnd.up:1&lt;/b&gt;&lt;/span&gt;(pwdUpdateEnd.up 의 첫번째 줄에서부터 오류가 난 것)&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 부분과,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 인증코드를 잘못 작성했을 때는 정상작동되고, 인증코드를 &lt;span style=&quot;color: #ee2323;&quot;&gt;&lt;b&gt;올바르게 입력했을 때만 오류가 발생&lt;/b&gt;&lt;/span&gt;한다는 점&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;을 고려하면&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;인증코드를 올바르게 입력했을 때 &lt;b&gt;페이지를 넘겨주는 부분&lt;/b&gt;에서 &lt;b&gt;문제가 발생&lt;/b&gt;했을 것으로 추측해볼 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1315&quot; data-origin-height=&quot;303&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/XblPB/btrMgnoLjXd/ff4qGjiONStBFklQqdMuV0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/XblPB/btrMgnoLjXd/ff4qGjiONStBFklQqdMuV0/img.png&quot; data-alt=&quot;인증코드를 올바르게 입력했을 때 페이지를 넘겨주는 부분( 사진상의 if문)&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/XblPB/btrMgnoLjXd/ff4qGjiONStBFklQqdMuV0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FXblPB%2FbtrMgnoLjXd%2Fff4qGjiONStBFklQqdMuV0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1315&quot; height=&quot;303&quot; data-origin-width=&quot;1315&quot; data-origin-height=&quot;303&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;인증코드를 올바르게 입력했을 때 페이지를 넘겨주는 부분( 사진상의 if문)&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;if문의 loc 부분 코드에서 문제가 생긴 것으로 추측 가능&lt;/p&gt;
&lt;pre id=&quot;code_1663307431986&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;loc = request.getContextPath()+&quot;/login/pwdUpdateEnd.up?userid=&quot;+userid;&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 부분에서 문제가 발생했다면 userid 부분에서 오류가 있었을 가능성이 가장 높기 때문에&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1236&quot; data-origin-height=&quot;317&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/reMn6/btrMhXpH9Vy/NXSgKWbKnaa1IqmaWrr6kK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/reMn6/btrMhXpH9Vy/NXSgKWbKnaa1IqmaWrr6kK/img.png&quot; data-alt=&quot;수정 - 1&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/reMn6/btrMhXpH9Vy/NXSgKWbKnaa1IqmaWrr6kK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FreMn6%2FbtrMhXpH9Vy%2FNXSgKWbKnaa1IqmaWrr6kK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1236&quot; height=&quot;317&quot; data-origin-width=&quot;1236&quot; data-origin-height=&quot;317&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;수정 - 1&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;pre id=&quot;code_1663307554133&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;loc = request.getContextPath()+&quot;/login/pwdUpdateEnd.up&quot;;&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이렇게 userid 부분을 제외하고 실행시켜 보니까&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;620&quot; data-origin-height=&quot;658&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/mZijO/btrMiT8b4Vm/Og0M0KKy3UkUVlLRWJkhqK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/mZijO/btrMiT8b4Vm/Og0M0KKy3UkUVlLRWJkhqK/img.png&quot; data-alt=&quot;수정 - 1 실행&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/mZijO/btrMiT8b4Vm/Og0M0KKy3UkUVlLRWJkhqK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FmZijO%2FbtrMiT8b4Vm%2FOg0M0KKy3UkUVlLRWJkhqK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;397&quot; height=&quot;658&quot; data-origin-width=&quot;620&quot; data-origin-height=&quot;658&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;수정 - 1 실행&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;페이지가 넘어갔다.!!!&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그러면 userid 부분에서 오류가 발생한 것이 확실하기 때문에&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그 부분의 코드로 넘어가서 userid 를 확인해본다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1507&quot; data-origin-height=&quot;503&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/rGRn4/btrMfesgujw/3MwiqADaD1UXDedrTXWDr1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/rGRn4/btrMfesgujw/3MwiqADaD1UXDedrTXWDr1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/rGRn4/btrMfesgujw/3MwiqADaD1UXDedrTXWDr1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FrGRn4%2FbtrMfesgujw%2F3MwiqADaD1UXDedrTXWDr1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1507&quot; height=&quot;503&quot; data-origin-width=&quot;1507&quot; data-origin-height=&quot;503&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;pre id=&quot;code_1663307857183&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;System.out.println(&quot;===userid :&quot; + userid);&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위의 코드를 넣어봐서 넘어온 userid 가 어떤 값을 가지는지 확인해본다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;983&quot; data-origin-height=&quot;177&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/buSDkE/btrMglLiFHh/qI4lshcZnJ9qcjx2n9IZMk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/buSDkE/btrMglLiFHh/qI4lshcZnJ9qcjx2n9IZMk/img.png&quot; data-alt=&quot;userid 값 확인해보기&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/buSDkE/btrMglLiFHh/qI4lshcZnJ9qcjx2n9IZMk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbuSDkE%2FbtrMglLiFHh%2FqI4lshcZnJ9qcjx2n9IZMk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;983&quot; height=&quot;177&quot; data-origin-width=&quot;983&quot; data-origin-height=&quot;177&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;userid 값 확인해보기&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;userid 값 확인 결과&lt;/p&gt;
&lt;pre id=&quot;code_1663308003714&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;=== userid : [object:Object]&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;userid 가 안넘어왔다,,,,,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그러면 userid 를 넘겨주는 부분으로 가보면&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1271&quot; data-origin-height=&quot;337&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bZIGAg/btrMjdFgS18/KlHkkLFxC5HAladoIg8QOK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bZIGAg/btrMjdFgS18/KlHkkLFxC5HAladoIg8QOK/img.png&quot; data-alt=&quot;userid 값을 넘겨주는 부분&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bZIGAg/btrMjdFgS18/KlHkkLFxC5HAladoIg8QOK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbZIGAg%2FbtrMjdFgS18%2FKlHkkLFxC5HAladoIg8QOK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1271&quot; height=&quot;337&quot; data-origin-width=&quot;1271&quot; data-origin-height=&quot;337&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;userid 값을 넘겨주는 부분&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;!!!! 오류 발견 !!!!&lt;/p&gt;
&lt;pre id=&quot;code_1663308298965&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;frm.userid.value = $(&quot;input#userid&quot;);
frm.userCertificationCode.value = $(&quot;input#input_confirmCode&quot;).val();&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;여기서 userid 부분에 .val() 이 빠져있어서 값이 안넘어갔던 것이다,,,,,,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;lt;문제 해결&amp;gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1285&quot; data-origin-height=&quot;387&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bl1Bip/btrMhB8eHX2/1DMvUzqCnqr6x7t9KIZeLK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bl1Bip/btrMhB8eHX2/1DMvUzqCnqr6x7t9KIZeLK/img.png&quot; data-alt=&quot;userid 부분 수정하기&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bl1Bip/btrMhB8eHX2/1DMvUzqCnqr6x7t9KIZeLK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fbl1Bip%2FbtrMhB8eHX2%2F1DMvUzqCnqr6x7t9KIZeLK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1285&quot; height=&quot;387&quot; data-origin-width=&quot;1285&quot; data-origin-height=&quot;387&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;userid 부분 수정하기&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;pre id=&quot;code_1663308395204&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;frm.userid.value = $(&quot;input#userid&quot;).val();
frm.userCertificationCode.value = $(&quot;input#input_confirmCode&quot;).val();&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;올바르게 수정을 하고 프로그램을 작동해보면,&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;982&quot; data-origin-height=&quot;348&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/mW8Jk/btrMgmcrUFU/GDBlbs4xoklEUfh0k8NCVK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/mW8Jk/btrMgmcrUFU/GDBlbs4xoklEUfh0k8NCVK/img.png&quot; data-alt=&quot;userid 값 받기 성공&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/mW8Jk/btrMgmcrUFU/GDBlbs4xoklEUfh0k8NCVK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FmW8Jk%2FbtrMgmcrUFU%2FGDBlbs4xoklEUfh0k8NCVK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;982&quot; height=&quot;348&quot; data-origin-width=&quot;982&quot; data-origin-height=&quot;348&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;userid 값 받기 성공&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;pre id=&quot;code_1663308460934&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;=== userid: kimhw&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;값이 잘 넘어왔고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(마지막줄의 ~~~~~~~~~~~~~~~userid : null 은 무시해도 됨)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;647&quot; data-origin-height=&quot;681&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bvXaeU/btrMjdrJm82/GXRkKBZcas167Qn9JWdgV0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bvXaeU/btrMjdrJm82/GXRkKBZcas167Qn9JWdgV0/img.png&quot; data-alt=&quot;오류 해결!&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bvXaeU/btrMjdrJm82/GXRkKBZcas167Qn9JWdgV0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbvXaeU%2FbtrMjdrJm82%2FGXRkKBZcas167Qn9JWdgV0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;402&quot; height=&quot;681&quot; data-origin-width=&quot;647&quot; data-origin-height=&quot;681&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;오류 해결!&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;값이 잘 넘어오는 것을 볼 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;문제 해결!&lt;/b&gt;&lt;/p&gt;</description>
      <category>오류 해결</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/142</guid>
      <comments>https://brissy.tistory.com/142#entry142comment</comments>
      <pubDate>Fri, 16 Sep 2022 15:10:57 +0900</pubDate>
    </item>
    <item>
      <title>JSTL(JSP Standard Tag Library) - 7. 포맷(fmt) 태그</title>
      <link>https://brissy.tistory.com/141</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;fmt&amp;nbsp;태그는&amp;nbsp;Formatting&amp;nbsp;태그로&amp;nbsp;포맷에&amp;nbsp;관련된&amp;nbsp;태그입니다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;실행 파일&lt;/p&gt;
&lt;pre id=&quot;code_1662041930862&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;&amp;lt;%@ page language=&quot;java&quot; contentType=&quot;text/html; charset=UTF-8&quot;
    pageEncoding=&quot;UTF-8&quot;%&amp;gt;

    
&amp;lt;%
   String[] pointArr1 = {&quot;10&quot;,&quot;20.4&quot;,&quot;30.5&quot;,&quot;46&quot;};
   request.setAttribute(&quot;pointArr1&quot;, pointArr1);
   
   String[] pointArr2 = null;
   request.setAttribute(&quot;pointArr2&quot;, pointArr2);
   
   int[] priceArr = {50000, 100000, 250000, 150000, 2000000};
   request.setAttribute(&quot;priceArr&quot;, priceArr);   
   
   RequestDispatcher dispatcher = request.getRequestDispatcher(&quot;08_fmt_view_02.jsp&quot;); 
    dispatcher.forward(request, response);
%&amp;gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;view 파일&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;문자열로&amp;nbsp;되어진&amp;nbsp;숫자를&amp;nbsp;누적한&amp;nbsp;결과값(자동형변환,&amp;nbsp;형변환)&amp;nbsp;나타내기&amp;nbsp;및&amp;nbsp;정수로&amp;nbsp;되어진&amp;nbsp;데이터를&amp;nbsp;세자리마다&amp;nbsp;콤마를&amp;nbsp;찍어서&amp;nbsp;나타내어주기&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;lt;&lt;span style=&quot;color: #ef6f53;&quot;&gt;fmt:parseNumber&lt;/span&gt;&amp;nbsp;var=&quot;&lt;span style=&quot;color: #a6bc00;&quot;&gt;pointInt&lt;/span&gt;&quot;&amp;nbsp;value=&quot;${point}&quot;&amp;nbsp;&lt;span style=&quot;color: #8a3db6;&quot;&gt;integerOnly=&quot;true&quot;&lt;/span&gt;&amp;nbsp;/&amp;gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #ef6f53;&quot;&gt;fmt:parseNumber&lt;/span&gt; 은 문자열을 숫자형식으로 형변환 시킨다. &lt;br /&gt;&lt;span style=&quot;color: #8a3db6;&quot;&gt;integerOnly=&quot;true&quot;&lt;/span&gt; 은 소수점은 절삭해버리고 정수만 취해온다. &lt;br /&gt;정수만 취해온 값을 변수 &lt;span style=&quot;color: #a6bc00;&quot;&gt;pointInt&lt;/span&gt; 에 넣어줌.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;lt;&lt;span style=&quot;color: #ef6f53;&quot;&gt;fmt:formatNumber&lt;/span&gt;&amp;nbsp;value=&quot;${price}&quot;&amp;nbsp;&lt;span style=&quot;color: #8a3db6;&quot;&gt;pattern=&quot;#,###&quot;&lt;/span&gt;&amp;nbsp;/&amp;gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #8a3db6;&quot;&gt;pattern=&quot;#,###&quot;&lt;/span&gt;:&amp;nbsp;숫자가&amp;nbsp;#,###&amp;nbsp;형식으로&amp;nbsp;출력됨&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre id=&quot;code_1662041954496&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;&amp;lt;%@ page language=&quot;java&quot; contentType=&quot;text/html; charset=UTF-8&quot;
    pageEncoding=&quot;UTF-8&quot;%&amp;gt;


&amp;lt;%-- ==== JSTL(JSP Standard Tag Library) 사용하기 ==== --%&amp;gt;     
&amp;lt;%@ taglib prefix=&quot;c&quot;   uri=&quot;http://java.sun.com/jsp/jstl/core&quot; %&amp;gt;
&amp;lt;%@ taglib prefix=&quot;fmt&quot; uri=&quot;http://java.sun.com/jsp/jstl/fmt&quot; %&amp;gt; 

&amp;lt;%--
     fmt 태그는 Formatting 태그로 포맷에 관련된 태그입니다.
         참조사이트  https://sinna94.tistory.com/11
--%&amp;gt;
   
    
&amp;lt;!DOCTYPE html&amp;gt;
&amp;lt;html&amp;gt;
&amp;lt;head&amp;gt;
&amp;lt;meta charset=&quot;UTF-8&quot;&amp;gt;
&amp;lt;title&amp;gt;문자열로 되어진 숫자를 누적한 결과값(자동형변환, 형변환) 나타내기 및 정수로 되어진 데이터를 세자리마다 콤마를 찍어서 나타내어주기&amp;lt;/title&amp;gt; 
&amp;lt;/head&amp;gt;
&amp;lt;body&amp;gt;
   &amp;lt;h2&amp;gt;문자열로 되어진 숫자를 누적한 결과값(자동형변환) 나타내기(JSTL을 사용한것)&amp;lt;/h2&amp;gt;
   
   &amp;lt;c:set var=&quot;sum&quot; value=&quot;0&quot; /&amp;gt; &amp;lt;%-- value=&quot;0&quot; 초기치는 항상 &quot;0&quot;(문자열) 이어야 함. 0이면 안됨 --%&amp;gt;
   &amp;lt;c:if test=&quot;${ not empty pointArr1 }&quot;&amp;gt; &amp;lt;!-- requestScope. 생략  --&amp;gt;
      &amp;lt;ul&amp;gt;
         &amp;lt;c:forEach var=&quot;point&quot; items=&quot;${pointArr1}&quot;&amp;gt;
            &amp;lt;li&amp;gt;${point}&amp;lt;/li&amp;gt;
            &amp;lt;c:set var=&quot;sum&quot; value=&quot;${sum + point}&quot; /&amp;gt;
         &amp;lt;/c:forEach&amp;gt; 
      &amp;lt;/ul&amp;gt;
      pointArr1 누적의 합계 : ${sum}
   &amp;lt;/c:if&amp;gt;
   
   &amp;lt;br&amp;gt;
   &amp;lt;hr style=&quot;border: solid 1px orange;&quot; /&amp;gt;
   &amp;lt;br&amp;gt;
   
   &amp;lt;h2&amp;gt;문자열로 되어진 숫자를 정수로 형변환하여 누적한 결과값 나타내기(JSTL을 사용한것)&amp;lt;/h2&amp;gt;
   
   &amp;lt;c:set var=&quot;sum&quot; value=&quot;0&quot; /&amp;gt;
   &amp;lt;c:if test=&quot;${ not empty pointArr1 }&quot;&amp;gt;
      &amp;lt;ul style=&quot;list-style-type: circle;&quot;&amp;gt;
         &amp;lt;c:forEach var=&quot;point&quot; items=&quot;${pointArr1}&quot;&amp;gt;
            &amp;lt;li&amp;gt;
               &amp;lt;fmt:parseNumber var=&quot;pointInt&quot; value=&quot;${point}&quot; integerOnly=&quot;true&quot; /&amp;gt;
               &amp;lt;%-- fmt:parseNumber 은 문자열을 숫자형식으로 형변환 시키는 것이다.
                    integerOnly=&quot;true&quot; 은 소수점은 절삭해버리고 정수만 취해오는 것이다.
                         정수만 취해온 값을 변수 pointInt 에 넣어줌.
               --%&amp;gt;
               ${pointInt}
            &amp;lt;/li&amp;gt;
            &amp;lt;c:set var=&quot;sum&quot; value=&quot;${sum + pointInt}&quot; /&amp;gt;
         &amp;lt;/c:forEach&amp;gt;
      &amp;lt;/ul&amp;gt;
      pointArr1 을 정수만 취해온 누적의 합계 : ${sum}
   &amp;lt;/c:if&amp;gt;
   
   &amp;lt;br&amp;gt;
   &amp;lt;hr style=&quot;border: solid 1px orange;&quot; /&amp;gt;
   &amp;lt;br&amp;gt;
   
   &amp;lt;h2&amp;gt;forEach 를 사용하면서 index번호를 나타내기&amp;lt;/h2&amp;gt;
   
   &amp;lt;c:if test=&quot;${ not empty pointArr1 }&quot;&amp;gt;
      &amp;lt;ul&amp;gt;
         &amp;lt;c:forEach var=&quot;point&quot; items=&quot;${pointArr1}&quot; varStatus=&quot;status&quot;&amp;gt; &amp;lt;%-- varStatus=&quot;이름은맘대로&quot;  --%&amp;gt;
            &amp;lt;li&amp;gt;${point}&amp;amp;nbsp;(인덱스번호 &amp;amp;nbsp; ${status.index})&amp;lt;/li&amp;gt;
            &amp;lt;%-- ${status.index} 은 0 부터 시작한다. --%&amp;gt;
         &amp;lt;/c:forEach&amp;gt;
      &amp;lt;/ul&amp;gt;
   &amp;lt;/c:if&amp;gt;

   &amp;lt;br&amp;gt;
   &amp;lt;hr style=&quot;border: solid 1px orange;&quot; /&amp;gt;
   &amp;lt;br&amp;gt;
   
   &amp;lt;h2&amp;gt;forEach 를 사용하면서 순서번호를 나타내기&amp;lt;/h2&amp;gt;
   
   &amp;lt;c:if test=&quot;${ not empty pointArr1 }&quot;&amp;gt;
      &amp;lt;ul&amp;gt;
         &amp;lt;c:forEach var=&quot;point&quot; items=&quot;${pointArr1}&quot; varStatus=&quot;status&quot;&amp;gt;
            &amp;lt;li&amp;gt;${point}&amp;amp;nbsp;(순서번호 &amp;amp;nbsp; ${status.count})&amp;lt;/li&amp;gt;
            &amp;lt;%-- ${status.count} 은 1 부터 시작한다. --%&amp;gt;
         &amp;lt;/c:forEach&amp;gt;
      &amp;lt;/ul&amp;gt;
   &amp;lt;/c:if&amp;gt;
   
   &amp;lt;br&amp;gt;
   &amp;lt;hr style=&quot;border: solid 1px blue;&quot; /&amp;gt;
   &amp;lt;br&amp;gt;
   
   &amp;lt;h2&amp;gt;정수로 되어진 데이터를 세자리 마다 콤마를 찍어서 나타내어 주기(JSTL을 사용한것)&amp;lt;/h2&amp;gt;
   
   &amp;lt;c:set var=&quot;sum&quot; value=&quot;0&quot; /&amp;gt;
   &amp;lt;c:if test=&quot;${ not empty priceArr }&quot;&amp;gt;
      &amp;lt;ul&amp;gt;
         &amp;lt;c:forEach var=&quot;price&quot; items=&quot;${priceArr}&quot;&amp;gt;
            &amp;lt;li&amp;gt;${price}&amp;lt;/li&amp;gt;
            &amp;lt;c:set var=&quot;sum&quot; value=&quot;${sum + price}&quot; /&amp;gt;
         &amp;lt;/c:forEach&amp;gt;
      &amp;lt;/ul&amp;gt;
      priceArr 누적의 합계 : ${sum}
   &amp;lt;/c:if&amp;gt;
   
   &amp;lt;br&amp;gt;&amp;lt;br&amp;gt;
   
   &amp;lt;c:set var=&quot;sum&quot; value=&quot;0&quot; /&amp;gt;
   &amp;lt;c:if test=&quot;${ not empty priceArr }&quot;&amp;gt;
      &amp;lt;ul&amp;gt;
         &amp;lt;c:forEach var=&quot;price&quot; items=&quot;${priceArr}&quot;&amp;gt;
            &amp;lt;li&amp;gt;&amp;lt;fmt:formatNumber value=&quot;${price}&quot; pattern=&quot;#,###&quot; /&amp;gt;&amp;lt;/li&amp;gt; &amp;lt;%-- pattern=&quot;#,###&quot;: 숫자가 #,### 형식으로 출력됨 --%&amp;gt;
            &amp;lt;c:set var=&quot;sum&quot; value=&quot;${sum + price}&quot; /&amp;gt;
         &amp;lt;/c:forEach&amp;gt;
      &amp;lt;/ul&amp;gt;
      priceArr 누적의 합계 : &amp;lt;fmt:formatNumber value=&quot;${sum}&quot; pattern=&quot;#,###&quot; /&amp;gt;
   &amp;lt;/c:if&amp;gt;
   
&amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;&lt;/code&gt;&lt;/pre&gt;</description>
      <category>JSP</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/141</guid>
      <comments>https://brissy.tistory.com/141#entry141comment</comments>
      <pubDate>Thu, 1 Sep 2022 23:22:41 +0900</pubDate>
    </item>
    <item>
      <title>JSTL(JSP Standard Tag Library) - 6. 함수 태그(functions)</title>
      <link>https://brissy.tistory.com/140</link>
      <description>&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;1865&quot; data-origin-height=&quot;887&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/DyjTH/btrK4FKHBcc/BjmrkM4lF6jBllrClbqeNK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/DyjTH/btrK4FKHBcc/BjmrkM4lF6jBllrClbqeNK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/DyjTH/btrK4FKHBcc/BjmrkM4lF6jBllrClbqeNK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FDyjTH%2FbtrK4FKHBcc%2FBjmrkM4lF6jBllrClbqeNK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;1865&quot; height=&quot;887&quot; data-origin-width=&quot;1865&quot; data-origin-height=&quot;887&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre id=&quot;code_1661956641839&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;        === 함수 태그(functions) ===
  
  JSTL은 EL에서 사용할 수 있는 함수 태그를 제공한다.
 
 -------------------------------------------------------------------------------------   
     함수                                                   설명
 -------------------------------------------------------------------------------------   
  length(obj)                      obj가 Conllection인 경우 저장된 항목의 개수를, 문자인 경우 문자열의 길이를 반환
  toUpperCase(str)                 str을 대문자로 변환
  toLowerCase(str)                 str을 소문자로 변환
  substring(str, idx1, idx2)       str.substring(idx1, idx2)의 결과를 반환, idx2가 -1일 경우 str.substring(idx1)과 동일
  substringAfter(str1, str2)       str1에서 str1에 포함되어 있는 str2 이후의 문자열을 구함
  substringBefore(str1, str2)      str1에서 str1에 포함되어 있는 str2 이전의 문자열을 구함
  trim(str)                        str 좌우의 공백 문자를 제거 
  replace(str, src, dest)          str에 있는 src를 dest로 변환
  indexOf(str1, str2)              str1에서 str2가 위치한 인덱스를 구함
  startsWith(str1, str2)           str1이 str2로 시작할 경우 true, 그렇지 않을 경우 false를 반환
  endsWith(str1, str2)             str1이 str2로 끝나는 경우 true, 그렇지 안을 경우 false를 반환
  contains(str1, str2)             st1이 str2를 포함하고 있을 경우 true를 반환
  containsIgnoreCase(str1, str2)   대소문자 구분없이 str1이 str2를 포함하고 있을 경우 true를 반환
  split(str1, str2)                str2로 명시한 글자를 기준으로 str1을 분리해서 배열로 반환 
  join(array, str2)                array에 저장된 문자열을 합침, 각 문자열의 사이에는 str2가 붙음&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;hr contenteditable=&quot;false&quot; data-ke-type=&quot;horizontalRule&quot; data-ke-style=&quot;style6&quot; /&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>JSP</category>
      <author>에어팟맥스</author>
      <guid isPermaLink="true">https://brissy.tistory.com/140</guid>
      <comments>https://brissy.tistory.com/140#entry140comment</comments>
      <pubDate>Wed, 31 Aug 2022 23:38:25 +0900</pubDate>
    </item>
  </channel>
</rss>