Dandy Now!
  • [개발자의품격][부트캠프][1기][13차시] JavaScript 주요 포인트 #19 | DOM 패턴 - 모달과 고객정보 수정
    2022년 02월 23일 00시 09분 06초에 업로드 된 글입니다.
    작성자: DandyNow
    728x90
    반응형

    JavaScript 주요 포인트 #19

    DOM 패턴 - 모달과 고객정보 수정

    Step 1

    [그림 1] 고객정보 수정 모달창

     

     

    <!-- dom_modal.html-->
    <!DOCTYPE html>
    <html lang="ko">
      <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Document</title>
        <style>
          .normal-table {
            border: 1px solid black;
            border-collapse: collapse;
            width: 100%;
          }
    
          .normal-table th,
          .normal-table td {
            border: 1px solid black;
            padding: 5px 10px;
          }
    
          .normal-table thead tr {
            background-color: yellow;
          }
          
          .striped tbody tr:nth-child(odd) {
            background-color: grey;
          }
    
          .hover tbody tr:hover {
            background-color: yellow;
          }
        </style>
        <!-- 모달 스타일 연결 / openModal 함수 호출전에는 모달창이 화면에 보이지 않는다. -->
        <link rel="stylesheet" href="css/modal.css" />
      </head>
      <body>
        <select name="" id="gender">
          <option value="">전체</option>
          <option value="male">남자</option>
          <option value="female">여자</option>
        </select>
        <input
          type="search"
          name=""
          id="searchName"
          placeholder="Name"
          onkeyup="checkEnter(event);"
        />
        <button onclick="doSearch();">조회</button>
        <button onclick="goToCreate();">생성</button>
        <button onclick="doDelete();" id="btnDelete" disabled>삭제</button>
        <table class="normal-table striped">
          <thead>
            <tr>
              <th><input type="checkbox" id="chks" onchange="checkAll()" /></th>
              <th>Name</th>
              <th>Company</th>
              <th>Gender</th>
              <th>Email</th>
              <th>Phone</th>
              <th>Addres</th>
            </tr>
          </thead>
          <tbody id="tbBody"></tbody>
        </table>
        <!-- 고객정보 수정 모달 -->
        <!-- modal-mask는 모달창 바깥 어두운 영역 -->
        <div class="modal-mask">
          <div class="modal-wrapper">
            <!-- modal-container는 모달창 영역 -->
            <div class="modal-container" style="width: 600px">
              <div class="modal-header">
                <h3>고객정보 수정</h3>
              </div>
              <div class="modal-body">
                <div class="row">
                  <div class="col-4">
                    <label for="name">Name</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="name" class="form-control" />
                    <input type="hidden" id="selectedId" value="" />
                  </div>
                  <div class="col-4">
                    <label for="name">Gender</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="radio"
                      name="gender"
                      id="male"
                      value="male"
                      checked
                    />
                    <label for="male">남자</label>
                    <input type="radio" name="gender" id="female" value="female" />
                    <label for="female">여자</label>
                  </div>
                  <div class="col-4">
                    <label for="company">Company</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="company" class="form-control" />
                  </div>
                  <div class="col-4">
                    <label for="email">Email</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="email"
                      name=""
                      id="email"
                      class="form-control"
                      onblur="checkEmail();"
                    />
                    <div id="emailMsg" class="alert" style="display: none">
                      올바른 형식의 이메일을 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="phone">Phone</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="tel"
                      name=""
                      id="phone"
                      class="form-control"
                      placeholder="010-0000-0000"
                      onblur="checkPhone();"
                    />
                    <div id="phoneMsg" class="alert" style="display: none">
                      올바른 형식의 연락처를 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="address">Address</label>
                  </div>
                  <div class="col-8">
                    <button onclick="openDaumAPI();">주소찾기</button>
                    <input
                      type="text"
                      name=""
                      id="zonecode"
                      style="width: 80px"
                      readonly
                    />
                    <input
                      type="text"
                      name=""
                      id="address"
                      class="form-control"
                      readonly
                    />
                  </div>
                </div>
              </div>
              <div class="modal-footer">
                <button onclick="doSave();">저장</button>
                <button onclick="closeModal();">닫기</button>
              </div>
            </div>
          </div>
        </div>
        <script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
        <script>
          async function doSearch() {
            const gender = document.querySelector("#gender").value;
            const name = document.querySelector("#searchName").value;
    
            let resource = "http://localhost:3000/customers";
            if (gender === "") {
              if (name !== "") {
                resource = `http://localhost:3000/customers?name_like=${name}`;
              }
            } else {
              if (name === "") {
                resource = `http://localhost:3000/customers?gender=${gender}`;
              } else {
                resource = `http://localhost:3000/customers?gender=${gender}&name_like=${name}`;
              }
            }
    
            const res = await fetch(resource);
            const resJson = await res.json();
            console.log(resJson);
            renderTable(resJson);
          }
    
          function renderTable(data) {
            customerData = data;
            const h = [];
            for (const item of data) {
              h.push("<tr>");
              h.push(
                `<td><input type="checkbox" value="${item.id}" name="chk" onchange="isChecked();" /></td>`
              );
              h.push(
                `<td><a href="javascript:openModal('${item.id}');">${item.name}</a></td>` // 이름에 정보 수정용 모달창을 띄우기 위한 링크 달기
              );
              h.push(`<td>${item.company}</td>`);
              h.push(`<td>${item.gender}</td>`);
              h.push(`<td>${item.email}</td>`);
              h.push(`<td>${item.phone}</td>`);
              h.push(`<td>${item.address}</td>`);
              h.push("</tr>");
            }
    
            document.querySelector("#tbBody").innerHTML = h.join("");
          }
    
          // 이름의 링크 클릭시 호출되는 openModal 함수
          function openModal(id) {
            console.log(id);
            document.querySelector(".modal-mask").className =
              "modal-mask modal-show";
          }
    
          // 닫기 버튼 클릭시 모달창 닫기
          function closeModal() {
            selectedId = "";
            document.querySelector(".modal-show").className = "modal-mask";
          }
    
          async function doDelete() {
            const chks = document.querySelectorAll("[name=chk]:checked");
    
            if (chks.length > 0) {
              if (confirm("정말 삭제하시겠습니까?")) {
                for (const chk of chks) {
                  await fetch(`http://localhost:3000/customers/${chks[0].value}`, {
                    method: "DELETE",
                  });
                }
    
                alert("데이터가 정상작으로 삭제 되었습니다.");
                await doSearch();
              }
            } else {
              alert("삭제할 아이템을 선택하세요.");
            }
          }
    
          function checkAll() {
            const checkValue = document.querySelector("#chks").checked;
            const chks = document.querySelectorAll("[name=chk]");
            for (const chk of chks) {
              chk.checked = checkValue;
            }
    
            isChecked();
          }
    
          function isChecked() {
            const chks = document.querySelectorAll("[name=chk]:checked");
            if (chks.length > 0) {
              document.querySelector("#btnDelete").disabled = false;
            } else {
              document.querySelector("#btnDelete").disabled = true;
            }
          }
    
          function goToCreate() {
            document.location.href = "dom_create.html";
          }
    
          function checkEnter(e) {
            // console.log(e);
            if (e.keyCode === 13) {
              doSearch();
            }
          }
    
          // 수정
          async function doSave() {
            const name = document.querySelector("#name").value.trim();
            const gender = document.querySelector("[name=gender]:checked").value;
            const company = document.querySelector("#company").value.trim();
            const email = document.querySelector("#email").value.trim();
            const phone = document.querySelector("#phone").value.trim();
            const address = document.querySelector("#address").value.trim();
    
            console.log(name);
            console.log(gender);
            console.log(company);
            console.log(email);
            console.log(phone);
            console.log(address);
    
            if (name === "") {
              return alert("Name을 입력하세요.");
            }
    
            if (company === "") {
              return alert("Company을 입력하세요.");
            }
    
            const regexpEmail = /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
            if (!regexpEmail.test(email)) {
              return alert("올바른 형식의 Email을 입력하세요.");
            }
    
            const regexpPhone = /^010-\d{3,4}-\d{4}$/;
            if (!regexpPhone.test(phone)) {
              return alert("올바른 형식의 Phone을 입력하세요.");
            }
    
            if (address === "") {
              return alert("Address을 입력하세요.");
            }
    
            const selectedId = document.querySelector("#selectedId").value;
    
            if (confirm("정말 저장하시겠습니까?")) {
              const res = await fetch(
                `http://localhost:3000/customers/${selectedId}`,
                {
                  method: "PUT", // 수정할때는 PUT
                  body: JSON.stringify({
                    name,
                    gender,
                    company,
                    email,
                    phone,
                    address,
                  }),
                  headers: {
                    "content-type": "application/json;charset=UTF-8",
                  },
                }
              );
    
              if (res.status === 200) {
                closeModal();
                alert("정상적으로 저장되었습니다.");
              } else {
                alert("고객 정보를 저장하지 못했습니다. 다시 시도하세요.");
              }
            }
          }
    
          function checkEmail() {
            const email = document.querySelector("#email").value;
            if (email !== "") {
              const regexpEmail =
                /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
              if (!regexpEmail.test(email)) {
                document.querySelector("#emailMsg").style.display = "block";
              } else {
                document.querySelector("#emailMsg").style.display = "none";
              }
            } else {
              document.querySelector("#emailMsg").style.display = "none";
            }
          }
    
          function checkPhone() {
            const phone = document.querySelector("#phone").value;
            if (phone !== "") {
              const regexpPhone = /^010-\d{3,4}-\d{4}$/;
              if (!regexpPhone.test(phone)) {
                document.querySelector("#phoneMsg").style.display = "block";
              } else {
                document.querySelector("#phoneMsg").style.display = "none";
              }
            } else {
              document.querySelector("#phoneMsg").style.display = "none";
            }
          }
    
          function openDaumAPI() {
            new daum.Postcode({
              oncomplete: function (data) {
                // 팝업에서 검색결과 항목을 클릭했을때 실행할 코드를 작성하는 부분입니다.
                // 예제를 참고하여 다양한 활용법을 확인해 보세요.
                console.log(data);
                document.querySelector("#address").value = data.address;
                document.querySelector("#zonecode").value = data.zonecode;
              },
            }).open();
          }
    
          function goToList() {
            document.location.href = "dom.html";
          }
    
          function doReset() {
            document.querySelector("#name").value = "";
            document.querySelector("#company").value = "";
            document.querySelector("#email").value = "";
            document.querySelector("#phone").value = "";
            document.querySelector("#address").value = "";
          }
        </script>
      </body>
    </html>

     


     

    Step 2

    [그림 2] 모달에 표시된 수정 대상의 정보

     

    <!-- dom_modal.html -->
    <!DOCTYPE html>
    <html lang="ko">
      <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Document</title>
        <style>
          .normal-table {
            border: 1px solid black;
            border-collapse: collapse;
            width: 100%;
          }
    
          .normal-table th,
          .normal-table td {
            border: 1px solid black;
            padding: 5px 10px;
          }
    
          .normal-table thead tr {
            background-color: yellow;
          }
          .striped tbody tr:nth-child(odd) {
            background-color: grey;
          }
    
          .hover tbody tr:hover {
            background-color: yellow;
          }
        </style>
        <link rel="stylesheet" href="css/modal.css" />
      </head>
      <body>
        <select name="" id="gender">
          <option value="">전체</option>
          <option value="male">남자</option>
          <option value="female">여자</option>
        </select>
        <input
          type="search"
          name=""
          id="searchName"
          placeholder="Name"
          onkeyup="checkEnter(event);"
        />
        <button onclick="doSearch();">조회</button>
        <button onclick="goToCreate();">생성</button>
        <button onclick="doDelete();" id="btnDelete" disabled>삭제</button>
        <table class="normal-table striped">
          <thead>
            <tr>
              <th><input type="checkbox" id="chks" onchange="checkAll()" /></th>
              <th>Name</th>
              <th>Company</th>
              <th>Gender</th>
              <th>Email</th>
              <th>Phone</th>
              <th>Addres</th>
            </tr>
          </thead>
          <tbody id="tbBody"></tbody>
        </table>
        <div class="modal-mask">
          <div class="modal-wrapper">
            <div class="modal-container" style="width: 600px">
              <div class="modal-header">
                <h3>고객정보 수정</h3>
              </div>
              <div class="modal-body">
                <div class="row">
                  <div class="col-4">
                    <label for="name">Name</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="name" class="form-control" />
                    <input type="hidden" id="selectedId" value="" />
                  </div>
                  <div class="col-4">
                    <label for="name">Gender</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="radio"
                      name="gender"
                      id="male"
                      value="male"
                      checked
                    />
                    <label for="male">남자</label>
                    <input type="radio" name="gender" id="female" value="female" />
                    <label for="female">여자</label>
                  </div>
                  <div class="col-4">
                    <label for="company">Company</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="company" class="form-control" />
                  </div>
                  <div class="col-4">
                    <label for="email">Email</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="email"
                      name=""
                      id="email"
                      class="form-control"
                      onblur="checkEmail();"
                    />
                    <div id="emailMsg" class="alert" style="display: none">
                      올바른 형식의 이메일을 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="phone">Phone</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="tel"
                      name=""
                      id="phone"
                      class="form-control"
                      placeholder="010-0000-0000"
                      onblur="checkPhone();"
                    />
                    <div id="phoneMsg" class="alert" style="display: none">
                      올바른 형식의 연락처를 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="address">Address</label>
                  </div>
                  <div class="col-8">
                    <button onclick="openDaumAPI();">주소찾기</button>
                    <input
                      type="text"
                      name=""
                      id="zonecode"
                      style="width: 80px"
                      readonly
                    />
                    <input
                      type="text"
                      name=""
                      id="address"
                      class="form-control"
                      readonly
                    />
                  </div>
                </div>
              </div>
              <div class="modal-footer">
                <button onclick="doSave();">저장</button>
                <button onclick="closeModal();">닫기</button>
              </div>
            </div>
          </div>
        </div>
        <script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
        <script>
          async function doSearch() {
            const gender = document.querySelector("#gender").value;
            const name = document.querySelector("#searchName").value;
    
            let resource = "http://localhost:3000/customers";
            if (gender === "") {
              if (name !== "") {
                resource = `http://localhost:3000/customers?name_like=${name}`;
              }
            } else {
              if (name === "") {
                resource = `http://localhost:3000/customers?gender=${gender}`;
              } else {
                resource = `http://localhost:3000/customers?gender=${gender}&name_like=${name}`;
              }
            }
    
            const res = await fetch(resource);
            const resJson = await res.json();
            console.log(resJson);
            renderTable(resJson);
          }
    
          let customerData = []; // 모달에 기본 정보 표시를 배열
    
          function renderTable(data) {
            customerData = data;
            const h = [];
            for (const item of data) {
              h.push("<tr>");
              h.push(
                `<td><input type="checkbox" value="${item.id}" name="chk" onchange="isChecked();" /></td>`
              );
              h.push(
                `<td><a href="javascript:openModal('${item.id}');">${item.name}</a></td>`
              );
              h.push(`<td>${item.company}</td>`);
              h.push(`<td>${item.gender}</td>`);
              h.push(`<td>${item.email}</td>`);
              h.push(`<td>${item.phone}</td>`);
              h.push(`<td>${item.address}</td>`);
              h.push("</tr>");
            }
    
            document.querySelector("#tbBody").innerHTML = h.join("");
          }
    
          let selectedId = ""; // 수정할 id
    
          // 모달에 기본 정보 표시
          function openModal(id) {
            console.log(id);
            // selectedId = id;
            selectedId = id; // 수정할 id
            let customer = customerData.filter((c) => c.id === id)[0];
            document.querySelector("#name").value = customer.name;
            document.querySelector("#company").value = customer.company;
            document.querySelector("#" + customer.gender).checked = true;
            document.querySelector("#email").value = customer.email;
            document.querySelector("#phone").value = customer.phone;
            document.querySelector("#address").value = customer.address;
    
            document.querySelector(".modal-mask").className =
              "modal-mask modal-show";
          }
    
          function closeModal() {
            selectedId = "";
            document.querySelector(".modal-show").className = "modal-mask";
          }
    
          async function doDelete() {
            const chks = document.querySelectorAll("[name=chk]:checked");
    
            if (chks.length > 0) {
              if (confirm("정말 삭제하시겠습니까?")) {
                for (const chk of chks) {
                  await fetch(`http://localhost:3000/customers/${chks[0].value}`, {
                    method: "DELETE",
                  });
                }
    
                alert("데이터가 정상작으로 삭제 되었습니다.");
                await doSearch();
              }
            } else {
              alert("삭제할 아이템을 선택하세요.");
            }
          }
    
          function checkAll() {
            const checkValue = document.querySelector("#chks").checked;
            const chks = document.querySelectorAll("[name=chk]");
            for (const chk of chks) {
              chk.checked = checkValue;
            }
    
            isChecked();
          }
    
          function isChecked() {
            const chks = document.querySelectorAll("[name=chk]:checked");
            if (chks.length > 0) {
              document.querySelector("#btnDelete").disabled = false;
            } else {
              document.querySelector("#btnDelete").disabled = true;
            }
          }
    
          function goToCreate() {
            document.location.href = "dom_create.html";
          }
    
          function checkEnter(e) {
            // console.log(e);
            if (e.keyCode === 13) {
              doSearch();
            }
          }
    
          async function doSave() {
            const name = document.querySelector("#name").value.trim();
            const gender = document.querySelector("[name=gender]:checked").value;
            const company = document.querySelector("#company").value.trim();
            const email = document.querySelector("#email").value.trim();
            const phone = document.querySelector("#phone").value.trim();
            const address = document.querySelector("#address").value.trim();
    
            console.log(name);
            console.log(gender);
            console.log(company);
            console.log(email);
            console.log(phone);
            console.log(address);
    
            if (name === "") {
              return alert("Name을 입력하세요.");
            }
    
            if (company === "") {
              return alert("Company을 입력하세요.");
            }
    
            const regexpEmail = /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
            if (!regexpEmail.test(email)) {
              return alert("올바른 형식의 Email을 입력하세요.");
            }
    
            const regexpPhone = /^010-\d{3,4}-\d{4}$/;
            if (!regexpPhone.test(phone)) {
              return alert("올바른 형식의 Phone을 입력하세요.");
            }
    
            if (address === "") {
              return alert("Address을 입력하세요.");
            }
    
            const selectedId = document.querySelector("#selectedId").value;
    
            if (confirm("정말 저장하시겠습니까?")) {
              const res = await fetch(
                `http://localhost:3000/customers/${selectedId}`, // ID 값 찾아 수정
                {
                  method: "PUT",
                  body: JSON.stringify({
                    name,
                    gender,
                    company,
                    email,
                    phone,
                    address,
                  }),
                  headers: {
                    "content-type": "application/json;charset=UTF-8",
                  },
                }
              );
    
              if (res.status === 200) {
                // 수정은 200번
                closeModal(); // 저장했으면 모달창을 닫는다.
                alert("정상적으로 저장되었습니다.");
              } else {
                alert("고객 정보를 저장하지 못했습니다. 다시 시도하세요.");
              }
            }
          }
    
          function checkEmail() {
            const email = document.querySelector("#email").value;
            if (email !== "") {
              const regexpEmail =
                /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
              if (!regexpEmail.test(email)) {
                document.querySelector("#emailMsg").style.display = "block";
              } else {
                document.querySelector("#emailMsg").style.display = "none";
              }
            } else {
              document.querySelector("#emailMsg").style.display = "none";
            }
          }
    
          function checkPhone() {
            const phone = document.querySelector("#phone").value;
            if (phone !== "") {
              const regexpPhone = /^010-\d{3,4}-\d{4}$/;
              if (!regexpPhone.test(phone)) {
                document.querySelector("#phoneMsg").style.display = "block";
              } else {
                document.querySelector("#phoneMsg").style.display = "none";
              }
            } else {
              document.querySelector("#phoneMsg").style.display = "none";
            }
          }
    
          function openDaumAPI() {
            new daum.Postcode({
              oncomplete: function (data) {
                // 팝업에서 검색결과 항목을 클릭했을때 실행할 코드를 작성하는 부분입니다.
                // 예제를 참고하여 다양한 활용법을 확인해 보세요.
                console.log(data);
                document.querySelector("#address").value = data.address;
                document.querySelector("#zonecode").value = data.zonecode;
              },
            }).open();
          }
    
          function goToList() {
            document.location.href = "dom.html";
          }
    
          function doReset() {
            document.querySelector("#name").value = "";
            document.querySelector("#company").value = "";
            document.querySelector("#email").value = "";
            document.querySelector("#phone").value = "";
            document.querySelector("#address").value = "";
          }
        </script>
      </body>
    </html>

     


     

    Step 3

    input type="hidden" 으로 수정할 ID를 지정한다.

    <!-- dom_modal.html -->
    <!DOCTYPE html>
    <html lang="ko">
      <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Document</title>
        <style>
          .normal-table {
            border: 1px solid black;
            border-collapse: collapse;
            width: 100%;
          }
    
          .normal-table th,
          .normal-table td {
            border: 1px solid black;
            padding: 5px 10px;
          }
    
          .normal-table thead tr {
            background-color: yellow;
          }
          .striped tbody tr:nth-child(odd) {
            background-color: grey;
          }
    
          .hover tbody tr:hover {
            background-color: yellow;
          }
        </style>
        <link rel="stylesheet" href="css/modal.css" />
      </head>
      <body>
        <select name="" id="gender">
          <option value="">전체</option>
          <option value="male">남자</option>
          <option value="female">여자</option>
        </select>
        <input
          type="search"
          name=""
          id="searchName"
          placeholder="Name"
          onkeyup="checkEnter(event);"
        />
        <button onclick="doSearch();">조회</button>
        <button onclick="goToCreate();">생성</button>
        <button onclick="doDelete();" id="btnDelete" disabled>삭제</button>
        <table class="normal-table striped">
          <thead>
            <tr>
              <th><input type="checkbox" id="chks" onchange="checkAll()" /></th>
              <th>Name</th>
              <th>Company</th>
              <th>Gender</th>
              <th>Email</th>
              <th>Phone</th>
              <th>Addres</th>
            </tr>
          </thead>
          <tbody id="tbBody"></tbody>
        </table>
        <div class="modal-mask">
          <div class="modal-wrapper">
            <div class="modal-container" style="width: 600px">
              <div class="modal-header">
                <h3>고객정보 수정</h3>
              </div>
              <div class="modal-body">
                <div class="row">
                  <div class="col-4">
                    <label for="name">Name</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="name" class="form-control" />
                    <!-- 사용자에게는 보이지 않는 숨겨진 입력 필드를 정의 -->
                    <input type="hidden" id="selectedId" value="" />
                  </div>
                  <div class="col-4">
                    <label for="name">Gender</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="radio"
                      name="gender"
                      id="male"
                      value="male"
                      checked
                    />
                    <label for="male">남자</label>
                    <input type="radio" name="gender" id="female" value="female" />
                    <label for="female">여자</label>
                  </div>
                  <div class="col-4">
                    <label for="company">Company</label>
                  </div>
                  <div class="col-8">
                    <input type="text" name="" id="company" class="form-control" />
                  </div>
                  <div class="col-4">
                    <label for="email">Email</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="email"
                      name=""
                      id="email"
                      class="form-control"
                      onblur="checkEmail();"
                    />
                    <div id="emailMsg" class="alert" style="display: none">
                      올바른 형식의 이메일을 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="phone">Phone</label>
                  </div>
                  <div class="col-8">
                    <input
                      type="tel"
                      name=""
                      id="phone"
                      class="form-control"
                      placeholder="010-0000-0000"
                      onblur="checkPhone();"
                    />
                    <div id="phoneMsg" class="alert" style="display: none">
                      올바른 형식의 연락처를 입력하세요.
                    </div>
                  </div>
                  <div class="col-4">
                    <label for="address">Address</label>
                  </div>
                  <div class="col-8">
                    <button onclick="openDaumAPI();">주소찾기</button>
                    <input
                      type="text"
                      name=""
                      id="zonecode"
                      style="width: 80px"
                      readonly
                    />
                    <input
                      type="text"
                      name=""
                      id="address"
                      class="form-control"
                      readonly
                    />
                  </div>
                </div>
              </div>
              <div class="modal-footer">
                <button onclick="doSave();">저장</button>
                <button onclick="closeModal();">닫기</button>
              </div>
            </div>
          </div>
        </div>
        <script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
        <script>
          async function doSearch() {
            const gender = document.querySelector("#gender").value;
            const name = document.querySelector("#searchName").value;
    
            let resource = "http://localhost:3000/customers";
            if (gender === "") {
              if (name !== "") {
                resource = `http://localhost:3000/customers?name_like=${name}`;
              }
            } else {
              if (name === "") {
                resource = `http://localhost:3000/customers?gender=${gender}`;
              } else {
                resource = `http://localhost:3000/customers?gender=${gender}&name_like=${name}`;
              }
            }
    
            const res = await fetch(resource);
            const resJson = await res.json();
            console.log(resJson);
            renderTable(resJson);
          }
    
          let customerData = [];
    
          function renderTable(data) {
            customerData = data;
            const h = [];
            for (const item of data) {
              h.push("<tr>");
              h.push(
                `<td><input type="checkbox" value="${item.id}" name="chk" onchange="isChecked();" /></td>`
              );
              h.push(
                `<td><a href="javascript:openModal('${item.id}');">${item.name}</a></td>`
              );
              h.push(`<td>${item.company}</td>`);
              h.push(`<td>${item.gender}</td>`);
              h.push(`<td>${item.email}</td>`);
              h.push(`<td>${item.phone}</td>`);
              h.push(`<td>${item.address}</td>`);
              h.push("</tr>");
            }
    
            document.querySelector("#tbBody").innerHTML = h.join("");
          }
    
          function openModal(id) {
            console.log(id);
            document.querySelector("#selectedId").value = id; // id 값을 input type hidden에 넣어 놓음
            let customer = customerData.filter((c) => c.id === id)[0];
            document.querySelector("#name").value = customer.name;
            document.querySelector("#company").value = customer.company;
            document.querySelector("#" + customer.gender).checked = true;
            document.querySelector("#email").value = customer.email;
            document.querySelector("#phone").value = customer.phone;
            document.querySelector("#address").value = customer.address;
    
            document.querySelector(".modal-mask").className =
              "modal-mask modal-show";
          }
    
          function closeModal() {
            selectedId = "";
            document.querySelector(".modal-show").className = "modal-mask";
          }
    
          async function doDelete() {
            const chks = document.querySelectorAll("[name=chk]:checked");
    
            if (chks.length > 0) {
              if (confirm("정말 삭제하시겠습니까?")) {
                for (const chk of chks) {
                  await fetch(`http://localhost:3000/customers/${chks[0].value}`, {
                    method: "DELETE",
                  });
                }
    
                alert("데이터가 정상작으로 삭제 되었습니다.");
                await doSearch();
              }
            } else {
              alert("삭제할 아이템을 선택하세요.");
            }
          }
    
          function checkAll() {
            const checkValue = document.querySelector("#chks").checked;
            const chks = document.querySelectorAll("[name=chk]");
            for (const chk of chks) {
              chk.checked = checkValue;
            }
    
            isChecked();
          }
    
          function isChecked() {
            const chks = document.querySelectorAll("[name=chk]:checked");
            if (chks.length > 0) {
              document.querySelector("#btnDelete").disabled = false;
            } else {
              document.querySelector("#btnDelete").disabled = true;
            }
          }
    
          function goToCreate() {
            document.location.href = "dom_create.html";
          }
    
          function checkEnter(e) {
            // console.log(e);
            if (e.keyCode === 13) {
              doSearch();
            }
          }
    
          async function doSave() {
            const name = document.querySelector("#name").value.trim();
            const gender = document.querySelector("[name=gender]:checked").value;
            const company = document.querySelector("#company").value.trim();
            const email = document.querySelector("#email").value.trim();
            const phone = document.querySelector("#phone").value.trim();
            const address = document.querySelector("#address").value.trim();
    
            console.log(name);
            console.log(gender);
            console.log(company);
            console.log(email);
            console.log(phone);
            console.log(address);
    
            if (name === "") {
              return alert("Name을 입력하세요.");
            }
    
            if (company === "") {
              return alert("Company을 입력하세요.");
            }
    
            const regexpEmail = /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
            if (!regexpEmail.test(email)) {
              return alert("올바른 형식의 Email을 입력하세요.");
            }
    
            const regexpPhone = /^010-\d{3,4}-\d{4}$/;
            if (!regexpPhone.test(phone)) {
              return alert("올바른 형식의 Phone을 입력하세요.");
            }
    
            if (address === "") {
              return alert("Address을 입력하세요.");
            }
    
            const selectedId = document.querySelector("#selectedId").value; // 수정할 #selectedId를 selectedID에 넣음. input type hidden은 수정할 Id를 지정하기 위해 사용하는 것이다.
    
            if (confirm("정말 저장하시겠습니까?")) {
              const res = await fetch(
                `http://localhost:3000/customers/${selectedId}`,
                {
                  method: "PUT",
                  body: JSON.stringify({
                    name,
                    gender,
                    company,
                    email,
                    phone,
                    address,
                  }),
                  headers: {
                    "content-type": "application/json;charset=UTF-8",
                  },
                }
              );
    
              if (res.status === 200) {
                closeModal();
                alert("정상적으로 저장되었습니다.");
              } else {
                alert("고객 정보를 저장하지 못했습니다. 다시 시도하세요.");
              }
            }
          }
    
          function checkEmail() {
            const email = document.querySelector("#email").value;
            if (email !== "") {
              const regexpEmail =
                /^([a-z]+\d*)+(\.?[a-z]*)+@[a-z]+(\.[a-z]{2,3})+$/;
              if (!regexpEmail.test(email)) {
                document.querySelector("#emailMsg").style.display = "block";
              } else {
                document.querySelector("#emailMsg").style.display = "none";
              }
            } else {
              document.querySelector("#emailMsg").style.display = "none";
            }
          }
    
          function checkPhone() {
            const phone = document.querySelector("#phone").value;
            if (phone !== "") {
              const regexpPhone = /^010-\d{3,4}-\d{4}$/;
              if (!regexpPhone.test(phone)) {
                document.querySelector("#phoneMsg").style.display = "block";
              } else {
                document.querySelector("#phoneMsg").style.display = "none";
              }
            } else {
              document.querySelector("#phoneMsg").style.display = "none";
            }
          }
    
          function openDaumAPI() {
            new daum.Postcode({
              oncomplete: function (data) {
                // 팝업에서 검색결과 항목을 클릭했을때 실행할 코드를 작성하는 부분입니다.
                // 예제를 참고하여 다양한 활용법을 확인해 보세요.
                console.log(data);
                document.querySelector("#address").value = data.address;
                document.querySelector("#zonecode").value = data.zonecode;
              },
            }).open();
          }
    
          function goToList() {
            document.location.href = "dom.html";
          }
    
          function doReset() {
            document.querySelector("#name").value = "";
            document.querySelector("#company").value = "";
            document.querySelector("#email").value = "";
            document.querySelector("#phone").value = "";
            document.querySelector("#address").value = "";
          }
        </script>
      </body>
    </html>

     

    728x90
    반응형
    댓글