<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>우당탕탙 it일지</title>
    <link>https://hyewon-s-dev.tistory.com/</link>
    <description>IT와 관련된 모든 것에 대해 공부한 내용을 정리합니다.</description>
    <language>ko</language>
    <pubDate>Tue, 28 Jul 2026 06:42:59 +0900</pubDate>
    <generator>TISTORY</generator>
    <ttl>100</ttl>
    <managingEditor>혜원s</managingEditor>
    <image>
      <title>우당탕탙 it일지</title>
      <url>https://tistory1.daumcdn.net/tistory/6286234/attach/d6d8d56b51024d73af5ccec0889fdfae</url>
      <link>https://hyewon-s-dev.tistory.com</link>
    </image>
    <item>
      <title>[가상 면접 사례로 배우는 대규모 시스템 설계 기초] 12장. 채팅 시스템 설계</title>
      <link>https://hyewon-s-dev.tistory.com/32</link>
      <description>&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;1:1 채팅에 집중한 앱: 페이스북 메신저, 위챗, 왓츠앱&lt;/li&gt;
&lt;li&gt;그룹채팅에 중점을 둔 업무용 앱: 슬랙&lt;/li&gt;
&lt;li&gt;대규모 그룹 소통과 latency가 낮은 음성 채팅에 집중한 앱: 디스코드&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;1단계: 문제 이해 및 설계 범위 확정&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;응답지연이 낮은 일대일 채팅 기능&lt;/li&gt;
&lt;li&gt;최대 100명까지 참여할 수 있는 그룹 채팅 기능&lt;/li&gt;
&lt;li&gt;(첨부파일은 지원하지 않아도 됨. 텍스트 메시지만)&lt;/li&gt;
&lt;li&gt;사용자 접속상태 표시 기능&lt;/li&gt;
&lt;li&gt;메시지 길이 제한 - 100,000자 이하&lt;/li&gt;
&lt;li&gt;[시간 가능하다면] 종단 간 암호화 지원&lt;/li&gt;
&lt;li&gt;채팅 이력은 영원히 보관되어야 함&lt;/li&gt;
&lt;li&gt;다양한 단말 지원. 하나의 계정으로 여러 단말에 동시 접속 지원 (아무래도 웹/앱 모두 지원되려면 ..)&lt;/li&gt;
&lt;li&gt;푸시 알림&lt;/li&gt;
&lt;li&gt;5천만 DAU 처리 가능해야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;2단계: 개략적 설계안 제시 및 동의 구하기&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;기본 기능
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;클라이언트로부터 메시지 수신&lt;/li&gt;
&lt;li&gt;메시지 수신자 결정 및 전달&lt;/li&gt;
&lt;li&gt;수신자가 접속(online) 상태가 아닌 경우에는 접속할 때까지 해당 메시지 보관&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;사용할 네트워크 통신 프로토콜을 결정해야 함
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;HTTP
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;현재 웹에서 가장 널리 사용되는 프로토콜&lt;/li&gt;
&lt;li&gt;keep alive 헤더를 사용함으로써 클라이언트와 서버 사이의 연결을 끊지 않고 계속 유지할 수 있어 효율적이고, TCP 핸드셰이크 횟수를 줄일 수 있음&lt;/li&gt;
&lt;li&gt;대중적인 채팅 프로그램들이 초기 HTTP 를 사용했음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;그러나, HTTP는 클라이언트가 연결을 만드는 프로토콜로, 서버에서 클라이언트로 임의 시점에 메시지를 보내는 데에 쉽게 쓰일 수 없음
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;서버가 연결을 만드는 것처럼 동작할 수 있도록 하기 위한 기법들 &amp;rarr; 폴링(polling), 롱 폴링(log polling), 웹소켓 등&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;폴링&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;클라이언트가 주기적으로 서버에게 새 메시지가 있는지 물어보는 방법&lt;/li&gt;
&lt;li&gt;폴링을 자주 할수록 비용이 올라가며, 답해줄 메시지가 없는 경우에는 서버 자원이 불필요하게 낭비됨&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;롱 폴링&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&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;li&gt;단점
&lt;ul style=&quot;list-style-type: disc;&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;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;웹 소켓&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;서버가 클라이언트에게 비동기(async) 메시지를 보낼 때 가장 널리 사용&lt;/li&gt;
&lt;li&gt;처음에는 HTTP 연결이지만, 특정 핸드셰이크 절차를 거쳐 웹 소켓 연결로 업그레이드 됨
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;지속적인 연결이 만들어지고 나면 서버는 클라이언트에게 비동기적으로 메시지를 전송할 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;HTTP/HTTPS 기본 포트번호를 그대로 사용하기 때문에, 방화벽이 있는 환경에서도 잘 동작함&lt;/li&gt;
&lt;li&gt;양방향 메시지 전송 가능&lt;/li&gt;
&lt;li&gt;유의할 점은 지속적으로 유지되어야 하기 때문에, 서버 측에서 연결 관리를 효율적으로 해야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;개략적 설계안&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;통신 프로토콜: 웹 소켓 사용&lt;/li&gt;
&lt;li&gt;회원가입, 로그인, 사용자 프로파일 등 대부분의 기능은 HTTP&lt;/li&gt;
&lt;li&gt;구현할 채팅 시스템을 3개의 부분으로 나눌 수 있음 &amp;rarr; 무상태, 상태유지(stateful), 제3자 서비스 연동&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;무상태 서비스&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;로그인, 회원가입, 사용자 프로파일 표시 등을 처리하는 전통적인 요청/응답 서비스&lt;/li&gt;
&lt;li&gt;로드밸런서 뒤에 위치. 상당수가 시장에 완제품으로 나와있어 직접 구현하지 않아도 쉽게 사서 쓸 수 있음
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;서비스 탐색(service discovery) 서비스: 클라이언트가 접속할 채팅 서버의 DNS 호스트명을 클라이언트에게 알려주는 역할&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;상태 유지 서비스&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&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;h4 data-ke-size=&quot;size20&quot;&gt;제3자 서비스 연동&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;푸시 알람&lt;/li&gt;
&lt;li&gt;새 메시지를 받았다면, 설사 앱이 실행 중이지 않더라도 알람을 받아야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;규모 확장성&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;동시 접속자: 1M(100만) 라고 가정&lt;/li&gt;
&lt;li&gt;접속 당 10K(1만) 의 서버 메모리가 필요하다면, 10GB 메모리만 있으면 모든 연결을 다 처리할 수 있음&lt;/li&gt;
&lt;li&gt;초반 설계안에 서버 1대로 구성하는 것은 괜찮으나, SPOF(Single Point Of Failure) 과 같이 장애 대응을 위해서라도, 점차 다듬어가며 서버 여러 대로 트래픽 처리하기 위해 검토하기&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;개략적 설계안&lt;/h4&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;ch12_design.png&quot; data-origin-width=&quot;701&quot; data-origin-height=&quot;592&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cFDswq/dJMcafkAWbF/eSahjO81Ucf2kMNNwaJUvk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cFDswq/dJMcafkAWbF/eSahjO81Ucf2kMNNwaJUvk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cFDswq/dJMcafkAWbF/eSahjO81Ucf2kMNNwaJUvk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcFDswq%2FdJMcafkAWbF%2FeSahjO81Ucf2kMNNwaJUvk%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;752&quot; height=&quot;635&quot; data-filename=&quot;ch12_design.png&quot; data-origin-width=&quot;701&quot; data-origin-height=&quot;592&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;채팅 서버는 클라이언트 사이에 메시지를 중계하는 역할을 담당&lt;/li&gt;
&lt;li&gt;접속상태 서버는 사용자의 접속 여부를 관리&lt;/li&gt;
&lt;li&gt;API 서버는 로그인, 회원가입, 프로파일 변경 등 그 외 나머지 전부를 처리&lt;/li&gt;
&lt;li&gt;알람 서버는 푸시 알림을 보냄&lt;/li&gt;
&lt;li&gt;키-값 저장소에는 채팅 이력(history) 을 보관한다. 시스템에 접속한 사용자는 이전 채팅 이력을 전부 볼 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;저장소&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;데이터의 유형과 읽기/쓰기 연산의 패턴을 바탕으로, 관계형 데이터베이스를 쓸지, NoSQL을 채택할지 결정&lt;/li&gt;
&lt;li&gt;채팅 시스템이 다루는 데이터 2가지
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;(1) 사용자 프로파일, 설정, 친구 목록처럼 일반적인 데이터
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;안정성을 보장하는 관계형 DB에 저장&lt;/li&gt;
&lt;li&gt;다중화(replication)와 샤딩(sharding) 기술 사용&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;(2) 채팅 시스템에 대한 고유 데이터인 채팅 이력 데이터
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;(채팅 이력 데이터에 대한) 읽기/쓰기 패턴
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;채팅 이력 데이터의 양은 엄청나다. 페이스북 메신저/WhatsApp 기준 매일 600억 개의 메시지&lt;/li&gt;
&lt;li&gt;이 데이터 가운데 빈번하게 사용되는 것은 주로 최근에 주고받은 메시지이며, 대부분의 사용자는 오래된 메시지를 들여다보지 않음&lt;/li&gt;
&lt;li&gt;사용자는 대체로 최근에 주고받은 메시지 데이터만 보게 되는 것이 사실이나, 검색 기능을 이용하거나, 특정 사용자가 멘션된 메시지를 보거나, 특정 메시지로 점프 하거나 하여 무작위적인 데이터 접근을 하게되는 일도 있음. &amp;rarr; 전부 지원해야 함&lt;/li&gt;
&lt;li&gt;1:1 채팅 앱의 경우 읽기:쓰기 비율은 대략 1:1&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;위 모두를 지원하는 저장소인 &amp;lt;키-값 저장소&amp;gt;를 채택
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;키-값 저장소는 수평적 규모확장이 쉬움&lt;/li&gt;
&lt;li&gt;키-값 저장소는 데이터 접근 지연시간(latency)이 낮음&lt;/li&gt;
&lt;li&gt;관계형 데이터베이스는 데이터 가운데 long tail에 해당하는 부분을 잘 처리하지 못하는 경향이 있다. 인덱스가 커지면 데이터에 대한 무작위적 접근(random access)을 처리하는 비용이 늘어남&lt;/li&gt;
&lt;li&gt;이미 많은 안정적인 채팅 시스템이 키-값 저장소를 채택
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;페이스북 메신저: `HBase`, 디스코드: `카산드라`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;데이터 모델&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;메시지&amp;nbsp;데이터를&amp;nbsp;어떻게&amp;nbsp;보관할&amp;nbsp;것인지&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;&lt;span data-token-index=&quot;0&quot;&gt;1:1 채팅을 위한 메시지 테이블&lt;/span&gt;&lt;/h4&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;1_1.png&quot; data-origin-width=&quot;452&quot; data-origin-height=&quot;424&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/sP2tR/dJMcacBpbS1/RMdUMnzXZALz3vmlZ2Csek/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/sP2tR/dJMcacBpbS1/RMdUMnzXZALz3vmlZ2Csek/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/sP2tR/dJMcacBpbS1/RMdUMnzXZALz3vmlZ2Csek/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FsP2tR%2FdJMcacBpbS1%2FRMdUMnzXZALz3vmlZ2Csek%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;319&quot; height=&quot;299&quot; data-filename=&quot;1_1.png&quot; data-origin-width=&quot;452&quot; data-origin-height=&quot;424&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;기본 키(primary key): message_id&lt;/li&gt;
&lt;li&gt;created_at 으로는 메시지 순서를 정할 수 없음 &amp;rarr; 두 메시지가 동시에 만들어지는 경우&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;그룹 채팅을 위한 메시지 테이블&lt;/h4&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;group.png&quot; data-origin-width=&quot;456&quot; data-origin-height=&quot;442&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/oCYOH/dJMcafZctlN/27ZSoy5pmrZGOUxdxkl4R1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/oCYOH/dJMcafZctlN/27ZSoy5pmrZGOUxdxkl4R1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/oCYOH/dJMcafZctlN/27ZSoy5pmrZGOUxdxkl4R1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FoCYOH%2FdJMcafZctlN%2F27ZSoy5pmrZGOUxdxkl4R1%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-filename=&quot;group.png&quot; data-origin-width=&quot;456&quot; data-origin-height=&quot;442&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;복합 키(composite key): (channel_id, message_id)&lt;/li&gt;
&lt;li&gt;파티션 키: channel_id&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;message_id&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;message_id 는 메시지들의 순서도 표현할 수 있어야 하기 때문에, 아래와 같은 속성을 만족해야 함
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;message_id 의 값은 고유해야 함&lt;/li&gt;
&lt;li&gt;ID 값은 정렬 가능해야 하며 시간 순서와 일치해야 함. 즉, 새로운 ID는 이전 ID보다 큰 값이어야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;위 속성을 만족시키기 위한 방법
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;(1) auto_increment 사용 (RDBMS만 제공, NoSQL X) &amp;rarr; NoSQL인 키-값 저장소에서는 못 사용함&lt;/li&gt;
&lt;li&gt;(2) 스노플레이크 같은 전역적 64-bit 순서 번호 생성기 이용&lt;/li&gt;
&lt;li&gt;(3) 지역적 순서 번호 생성기
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;지역적 &amp;rarr; ID의 유일성이 같은 그룹 안에서만 보증하면 됨&lt;/li&gt;
&lt;li&gt;메시지 사이의 순서는 같은 채널, 혹은 1:1 채팅 세션 안에서만 유지되면 충분함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;3단계: 상세 설계&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;서비스 탐색(service discovery)&lt;/li&gt;
&lt;li&gt;메시지 전달 흐름&lt;/li&gt;
&lt;li&gt;사용자 접속 상태 표시&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;서비스 탐색&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;서비스 탐색 기능의 주된 역할은 클라이언트에게 가장 적합한 채팅 서버를 추천&lt;/li&gt;
&lt;li&gt;이 때 사용되는 기준으로는 클라이언트의 위치, 서버 용량 등이 있음&lt;/li&gt;
&lt;li&gt;ex. 아파치 주키퍼&lt;/li&gt;
&lt;li&gt;동작 순서
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li style=&quot;list-style: none;&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dna/BgSQN/dJMcad79uJf/AAAAAAAAAAAAAAAAAAAAAJPU5hprKIDwpu6ZKa_AuyM-5SsqtWN8_QZN5esiHPSR/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=L0yb0my4xtHwak3nai20fEwBLJo%3D&quot; width=&quot;526&quot; height=&quot;546&quot; data-image-src=&quot;https://blog.kakaocdn.net/dna/BgSQN/dJMcad79uJf/AAAAAAAAAAAAAAAAAAAAAJPU5hprKIDwpu6ZKa_AuyM-5SsqtWN8_QZN5esiHPSR/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=L0yb0my4xtHwak3nai20fEwBLJo%3D&quot; data-origin-width=&quot;503&quot; data-origin-height=&quot;522&quot; data-filename=&quot;제목 없는 다이어그램 (2).png&quot; /&gt;&lt;/li&gt;
&lt;li style=&quot;list-style: none;&quot;&gt;&amp;nbsp;&lt;/li&gt;
&lt;li&gt;1. 사용자가 시스템에 로그인 시도&lt;/li&gt;
&lt;li&gt;2. 로드밸런서가 로그인 요청을 API 서버들 가운데 하나로 보냄&lt;/li&gt;
&lt;li&gt;3. API 서버가 사용자 인증을 처리하고 나면 서비스 탐색 기능이 동작하여 해당 사용자를 서비스할 최적의 채팅 서버를 찾는다 (위 예제의 경우, 최적 채팅서버로 2번을 선택. 그림 참고)&lt;/li&gt;
&lt;li&gt;4. 사용자는 채팅서버 2와 웹소켓 연결을 맺음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;메시지 흐름&lt;/h3&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;1:1 채팅 메시지 처리 흐름&lt;/h4&gt;
&lt;ol style=&quot;list-style-type: decimal;&quot; data-ke-list-type=&quot;decimal&quot;&gt;
&lt;li&gt;사용자가 채팅서버 1로 메시지 전송&lt;/li&gt;
&lt;li&gt;채팅서버 1은 ID 생성기를 사용해 해당 메시지의 ID 결정&lt;/li&gt;
&lt;li&gt;채팅 서버 1은 해당 메시지를 메시지 동기화 큐로 전송&lt;/li&gt;
&lt;li&gt;메시지가 키-값 저장소에 보관됨&lt;/li&gt;
&lt;li&gt;(a) 사용자 B가 &lt;u&gt;접속 중&lt;/u&gt;인 경우 메시지는 사용자 B가 접속 중인 채팅 서버(본 예제에서는 채팅서버2) 로 전송됨&lt;br /&gt;(b) 사용자 B가 &lt;u&gt;접속 중이 아니라면&lt;/u&gt;&amp;nbsp;푸시 알림 메시지를 푸시 알림 서버로 보냄&lt;/li&gt;
&lt;li&gt;채팅 서버2는 메시지를 사용자 B에게 전송. 사용자 B와 채팅 서버2 사이에는 웹소켓 연결이 있는 상태이므로 그것을 이용&lt;/li&gt;
&lt;/ol&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;여러 단말 사이의 메시지 동기화&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;다음 두 조건을 만족하는 메시지는 새 메시지로 간주
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;수신자ID가 현재 로그인한 사용자ID와 같음&lt;/li&gt;
&lt;li&gt;키-값 저장소에 보관된 메시지로서, 그 ID가 cur_max_message_id 보다 큼&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;소규모 그룹 채팅에서의 메시지 흐름&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자 별로 메시지 동기화 큐(message sync queue) 로 구현
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;새로운 메시지가 왔는지 확인하려면 본인 큐만 보면 되기 때문에, 메시지 동기화 플로가 단순함&lt;/li&gt;
&lt;li&gt;그룹이 크지 않으면 수신자별로 복사하여 큐에 넣는 작업의 비용이 문제되지 않음&lt;/li&gt;
&lt;li&gt;&amp;rarr; 해당 방법은 사용자가 많으면 (똑같은 메시지를 모든 사용자의 큐에 복사하기 때문에) 바람직하지 않음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;접속상태 표시&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;접속상태 서버 사용하여 사용자 상태 관리&lt;/li&gt;
&lt;li&gt;접속상태 서버는 클라이언트와 웹소켓으로 통신하는 실시간 서비스의 일부&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;사용자 로그인&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;클라이언트와 실시간 서비스 사이에 웹소켓 연결이 맺어지고 나면, 접속상태 서버는 사용자의 status(online)와 timestamp 값을 키-값 저장소에 보관&lt;/li&gt;
&lt;li&gt;이 절차가 끝나고 나면 해당 사용자는 접속 중인 것으로 표시&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;로그아웃&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;키-값 저장소에 보관된 사용자 status 가 online &amp;rarr; offline 으로 바뀜&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;접속 장애&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자의 인터넷 연결이 끊어지면 클라이언트와 서버 사이에 맺어진 웹소켓 같은 지속성 연결이 끊김
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;간단한 해결 방법: 사용자를 오프라인 상태로 표시한 후, 연결이 복구되면 온라인 상태로 변경
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;짧은 시간 동안 인터넷 연결이 끊어졌다 복구되는 일은 흔하기 때문에, 그 때마다 상태를 변경한다면 지나친 일이고, 사용자 경험 측면에서도 바람직하지 않음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;heartbeat 검사를 통해 해결
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;온라인 상태의 클라이언트에게 주기적으로 heartbeat event를 접속상태 서버로 보내도록 하고, 마지막 이벤트를 받은 지 x초 이내에 또 다른 박동 이벤트 메시지를 받으면 해당 사용자의 접속상태를 계속 온라인으로 유지&lt;/li&gt;
&lt;li&gt;x초 이후에는 오프라인으로 바꿈&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;상태 정보의 전송&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자 A와 친구 관계에 있는 사용자들이 어떻게 상태변화를 알게 하는지&lt;/li&gt;
&lt;li&gt;발행-구독 모델(publish-subscribe model)을 사용하여 각각의 친구관계마다 채널을 하나씩 둠
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자 A 기준으로 B,C,D 친구가 있다면
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;채널 개수: 3개 (A-B, A-C, A-D)&lt;/li&gt;
&lt;li&gt;A의 구독자: B, C, D&lt;/li&gt;
&lt;li&gt;해당 채널을 통해 상태정보 변화 통지 받을 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;클라이언트와 서버 사이의 통신에는 실시간 웹소켓 사용&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;위 방법은 그룹 크기가 작을 때 효과적. 성능 문제를 해소하는 방법으로는, 사용자가 그룹 채팅에 입장하는 순간에만 상태정보를 읽어가게 하거나, 친구 리스트에 있는 사용자의 접속상태를 갱신하고 싶으면 수동으로 하도록 유도&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;4단계: 마무리&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;[정리] 1:1 채팅, 그룹 채팅을 지원하는 채팅 시스템
&lt;ul style=&quot;list-style-type: disc;&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;li&gt;푸시 알림 서버&lt;/li&gt;
&lt;li&gt;채팅 이력을 보관할 키-값 저장소&lt;/li&gt;
&lt;li&gt;이를 제외한 나머지 기능을 구현하는 데 쓰일 API 서버 등&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;이후에 논의해봐도 좋을 것
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;채팅 앱을 확장하여 사진이나 비디오 등의 미디어를 지원하도록 하는 방법
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사진, 비디오는 텍스트에 비해 크기가 크기 때문에, 이와 관련하여 압축 방식, 클라우드 저장소, 썸네일 생성 등을 논의&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;종단 간 암호화
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;메시지 발신인과 수신자 이외에는 아무도 메시지를 볼 수 없도록&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;캐시
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;클라이언트에 이미 읽은 메시지를 캐시해두어 서버와 주고받는 데이터의 양을 줄임&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;로딩 속도 개선
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자의 데이터, 채널 등을 지역적으로 분산하여 앱 로딩속도 개선 가능&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;오류 처리
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;채팅 서버 오류: 서버 하나가 죽으면, 해당 서버에 할당되어있는 클라이언트들에게 새로운 서버를 배정하고 다시 접속할 수 있도록 해야 함&lt;/li&gt;
&lt;li&gt;메시지 재전송: 재시도나 큐는 메시지의 안정적 전송을 보장&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;</description>
      <category>도서/대규모시스템설계기초1</category>
      <category>대규모시스템설계</category>
      <category>채팅시스템</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/32</guid>
      <comments>https://hyewon-s-dev.tistory.com/32#entry32comment</comments>
      <pubDate>Mon, 3 Nov 2025 17:29:13 +0900</pubDate>
    </item>
    <item>
      <title>[가상 면접 사례로 배우는 대규모 시스템 설계 기초] 6장. 키-값 저장소 설계</title>
      <link>https://hyewon-s-dev.tistory.com/31</link>
      <description>&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;키-값 저장소 (key-value store)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;비관계형(non-relational) 데이터베이스&lt;/li&gt;
&lt;li&gt;이 저장소에 저장되는 값은 고유 식별자(identifier)를 키로 가져와야 함&lt;/li&gt;
&lt;li&gt;키-값을 쌍(pair)이라 지칭&lt;/li&gt;
&lt;li&gt;값(value)은 문자열, 리스트, object 등 무엇이 오든 상관하지 않음&lt;/li&gt;
&lt;li&gt;ex. 아마존 다이나모, memcached, redis 등&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;이번 장에서는 put, get 연산을 지원하는 키-값 저장소 설계&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;&lt;span data-token-index=&quot;0&quot;&gt;문제 이해 및 설계 범위 확정&lt;/span&gt;&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;키-값 쌍의 크기는 10KB 이하&lt;/li&gt;
&lt;li&gt;큰 데이터를 저장할 수 있어야 함&lt;/li&gt;
&lt;li&gt;높은 가용성 제공 &amp;rarr; 장애가 있더라도 빨리 응답해야 함&lt;/li&gt;
&lt;li&gt;높은 규모 확장성 제공 &amp;rarr; 트래핑 양에 따라 자동적으로 서버 증설/삭제가 이루어져야 함&lt;/li&gt;
&lt;li&gt;데이터 일관성 수준은 조정이 가능해야 함&lt;/li&gt;
&lt;li&gt;latency가 짧아야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;&lt;span data-token-index=&quot;0&quot;&gt;단일 서버 키-값 저장소&lt;/span&gt;&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;가장 직관적인 방법&lt;/li&gt;
&lt;li&gt;키-값 쌍 전부를 메모리에 해시 테이블로 저장&lt;/li&gt;
&lt;li&gt;모든 데이터를 메모리 안에 두는 것이 불가능. 설령 디스크를 활용하더라도 서버 1대로 부족해질 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;&lt;span data-token-index=&quot;0&quot;&gt;분산 서버 키-값 저장소&lt;/span&gt;&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;분산 해시 테이블&lt;/li&gt;
&lt;li&gt;키-값 쌍을 여러 서버에 분산시킴&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;CAP 정리&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;분산 시스템 설계를 위해 필요한 정리&lt;/li&gt;
&lt;li&gt;데이터 일관성 (Consistency)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;분산 시스템에 접속하는 모든 클라이언트는 어떤 노드에 접속했느냐에 관계없이 언제나 같은 데이터를 보게 되어야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;가용성 (Availability)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;분산 시스템에 접속하는 클라이언트는 일부 노드에 장애가 발생하더라도 항상 응답을 받을 수 있어야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;파티션 감내 (Partition tolerance)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;파티션은 두 노드 사이에 통신 장애가 발생하였음을 의미함&lt;/li&gt;
&lt;li&gt;네트워크 파티션이 생기더라도 시스템은 계속 동작하여야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;세 가지 요구사항을 동시에 만족하는 분산 시스템을 설계하는 것은 불가능&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;CP 시스템
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;일관성과 파티션 감내를 지원하는 키-값 저장소&lt;/li&gt;
&lt;li&gt;가용성 희생&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;AP 시스템
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;가용성과 파티션 감내를 지원하는 키-값 저장소&lt;/li&gt;
&lt;li&gt;데이터 일관성 희생&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;CA 시스템
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;일관성과 가용성을 지원하는 키-값 저장소&lt;/li&gt;
&lt;li&gt;파티션 감내 지원하지 않음&lt;/li&gt;
&lt;li&gt;그러나, 네트워크 장애는 피할 수 없는 일로 여겨지므로 파티션 문제는 반드시 감내할 수 있도록 설계되어야하기 때문에,&amp;nbsp;&lt;span style=&quot;color: #ef5369;&quot;&gt;&lt;b&gt;CA 시스템은 존재하지 않음&lt;/b&gt;&lt;/span&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;이상적 형태&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;파티션되는 상황이 절대로 일어나지 않음&lt;/li&gt;
&lt;li&gt;n1에 기록된 데이터는 자동적으로 n2와 n3에 복제 (n 은 노드)&lt;/li&gt;
&lt;li&gt;데이터 일관성과 가용성도 만족&lt;/li&gt;
&lt;/ul&gt;
&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;221&quot; data-origin-height=&quot;216&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/3izLU/dJMcai2F7n2/61FQ1SWGYLDjkJo3hNkVUK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/3izLU/dJMcai2F7n2/61FQ1SWGYLDjkJo3hNkVUK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/3izLU/dJMcai2F7n2/61FQ1SWGYLDjkJo3hNkVUK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F3izLU%2FdJMcai2F7n2%2F61FQ1SWGYLDjkJo3hNkVUK%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;221&quot; height=&quot;216&quot; data-filename=&quot;제목 없는 다이어그램.png&quot; data-origin-width=&quot;221&quot; data-origin-height=&quot;216&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;실세계의 분산 시스템&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;파티션 문제 발생 시, 일관성과 가용성 사이에서 하나 선택해야 함&lt;/li&gt;
&lt;li&gt;n3 장애 발생&amp;nbsp;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;n1, n2에 기록된 데이터는 n3에 전달되지 않음&lt;/li&gt;
&lt;li&gt;n3에 기록되었으나 n1, n2로 전달되지 않은 데이터가 있다면, n1, n2가 가지고 있는 데이터는 오래된 데이터를 가지고 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;227&quot; data-origin-height=&quot;216&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/7SKPo/dJMcaf5Xd2s/MuO62H3GKSDjK1JZPaMjS0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/7SKPo/dJMcaf5Xd2s/MuO62H3GKSDjK1JZPaMjS0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/7SKPo/dJMcaf5Xd2s/MuO62H3GKSDjK1JZPaMjS0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F7SKPo%2FdJMcaf5Xd2s%2FMuO62H3GKSDjK1JZPaMjS0%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;227&quot; height=&quot;216&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;227&quot; data-origin-height=&quot;216&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;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;일관성 선택 시(CP 시스템), 데이터 불일치 문제를 피하기 위해 n1, n2의 쓰기 연산 중단. 일반적으로 은행권 시스템에서 사용&lt;/li&gt;
&lt;li&gt;가용성 선택 시(AP 시스템), 낡은 데이터를 반환할 위험이 있더라도 계속 읽기 연산 허용&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;시스템 컴포넌트&lt;/h2&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;데이터 파티션&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;데이터 파티션을 나눌 때 중요하게 봐야할 부분
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;데이터를 여러 서버에 고르게 분산할 수 있는가&lt;/li&gt;
&lt;li&gt;노드가 추가되거나 삭제될 때 데이터의 이동을 최소화할 수 있는가&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;안정해시(consistent hash) 가 적합
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;규모 확장 자동화(automatic scaling): 시스템 부하에 따라 서버가 자동으로 추가되거나 삭제되도록 만들 수 있음&lt;/li&gt;
&lt;li&gt;다양성(heterogeneity): 각 서버의 용량에 맞게 가상노드의 수를 조정할 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (2).png&quot; data-origin-width=&quot;351&quot; data-origin-height=&quot;361&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/kF6ku/dJMcadUBpuC/YOwixW6Qtqn65pXmxvFOIK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/kF6ku/dJMcadUBpuC/YOwixW6Qtqn65pXmxvFOIK/img.png&quot; data-alt=&quot;안정해시 (5장에서 자세한 개념 확인 가능)&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/kF6ku/dJMcadUBpuC/YOwixW6Qtqn65pXmxvFOIK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FkF6ku%2FdJMcadUBpuC%2FYOwixW6Qtqn65pXmxvFOIK%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;351&quot; height=&quot;361&quot; data-filename=&quot;제목 없는 다이어그램 (2).png&quot; data-origin-width=&quot;351&quot; data-origin-height=&quot;361&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;안정해시 (5장에서 자세한 개념 확인 가능)&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;데이터 다중화&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;높은 가용성과 안정성 확보를 위해 필요&lt;/li&gt;
&lt;li&gt;어떤 키를 해시 링 위에 배치한 후, 그 지점으로부터 시계 방향으로 링을 순회하면서 만나는 첫 n개 서버에 데이터 사본 보관&lt;/li&gt;
&lt;/ul&gt;
&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;351&quot; data-origin-height=&quot;361&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/RorW6/dJMcake7DYx/k7ay8jiuQmVKlf0EVPpRJK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/RorW6/dJMcake7DYx/k7ay8jiuQmVKlf0EVPpRJK/img.png&quot; data-alt=&quot;n = 3 일 경우의 예시. 서버 3개에 저장됨&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/RorW6/dJMcake7DYx/k7ay8jiuQmVKlf0EVPpRJK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FRorW6%2FdJMcake7DYx%2Fk7ay8jiuQmVKlf0EVPpRJK%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;362&quot; height=&quot;372&quot; data-filename=&quot;제목 없는 다이어그램.png&quot; data-origin-width=&quot;351&quot; data-origin-height=&quot;361&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;n = 3 일 경우의 예시. 서버 3개에 저장됨&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;실제 물리서버 개수는 n보다 작을 수 있으므로, 같은 물리서버를 중복 선택되지 않도록 해야함
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. 서버1: `s1, s4, s7` / 서버2: `s0, s2, s5` / 서버3: `s3, s6` &amp;rarr; 서버 3대에 노드 7개 올라가 있는 예시&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;같은 데이터 센터에 속한 노드는 정전, 네트워크 이슈, 자연재해 등의 문제를 동시에 겪을 수 있으므로, 안정성 담보를 위해 데이터의 사본은 다른 센터의 서버에 보관하고, 센터들은 고속 네트워크로 연결해야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;데이터 일관성&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;정족수의 합의(Quorum Consensus) 프로토콜 사용하여 읽기/쓰기 연산 모두에 일관성 보장할 수 있음&lt;/li&gt;
&lt;li&gt;변수 정의
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;N = 사본 개수&lt;/li&gt;
&lt;li&gt;W = 쓰기 연산에 대한 정족수. 쓰기 연산이 성공한 것으로 간주되려면 적어도 W개의 서버로부터 쓰기 연산이 성공했다는 응답을 받아야 함&lt;/li&gt;
&lt;li&gt;R = 읽기 연산에 대한 정족수. 읽기 연산이 성공한 것으로 간주되려면 적어도 R개의 서버로부터 읽기 연산이 성공했다는 응답을 받아야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;372&quot; data-origin-height=&quot;351&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/7NVOf/dJMcaj1AsCf/6JqGVscPe4tXGRbotV4raK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/7NVOf/dJMcaj1AsCf/6JqGVscPe4tXGRbotV4raK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/7NVOf/dJMcaj1AsCf/6JqGVscPe4tXGRbotV4raK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F7NVOf%2FdJMcaj1AsCf%2F6JqGVscPe4tXGRbotV4raK%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;431&quot; height=&quot;407&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;372&quot; data-origin-height=&quot;351&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;중재자: 클라이언트와 노드 사이에서의 프록시(proxy) 역할을 함&lt;/li&gt;
&lt;li&gt;W, R, N 값을 정하는 것은 &lt;u&gt;응답 지연&lt;/u&gt;과 &lt;u&gt;데이터 일관성&lt;/u&gt; 사이의 타협점을 찾는 과정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;W = 1 일 경우, 최소 한 대의 서버로부터 쓰기 성공 응답을 받아야 함. 중재자가 s1 의 쓰기 연산 성공 응답을 받았다면, s0, s2 응답은 기다릴 필요 없음&lt;/li&gt;
&lt;li&gt;W = 1 or R = 1 일 경우, 응답 속도가 빠름&lt;/li&gt;
&lt;li&gt;W, R &amp;gt; 1 일 경우, 데이터 일관성 수준이 향상되지만 응답 지연 발생할 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;구성 예시
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;R = 1, W = N : 빠른 읽기 연산에 최적화된 시스템&lt;/li&gt;
&lt;li&gt;W = 1, R = N : 빠른 쓰기 연산에 최적화된 시스템&lt;/li&gt;
&lt;li&gt;W + R &amp;gt; N: 강한 일관성이 보장됨 (보통 N=3, W=R=2)&lt;/li&gt;
&lt;li&gt;W + R &amp;lt;= N: 강한 일관성이 보장되지 않음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;일관성 모델&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;강한 일관성(strong consistency): 모든 읽기 연산은 가장 최근에 갱신된 결과를 반환. 클라이언트는 절대로 낡은(out-of-date) 데이터를 보지 못함
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&amp;rarr; 모든 사본에 쓰기 연산 결과가 반영될 때까지 새로운 요청 처리가 중단되기 때문에, 고가용성에 적합하지 않음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;약한 일관성(weak consistency): 읽기 연산은 가장 최근에 갱신된 결과를 반환하지 못할 수 있음&lt;/li&gt;
&lt;li&gt;결과적 일관성(eventual consistency): 약한 일관성의 한 형태로, 갱신 결과가 결국에는 모든 사본에 반영되는 모델
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&amp;rarr; Dynamo, Cassandra DB에서 채택하고 있음&lt;/li&gt;
&lt;li&gt;&amp;rarr; 쓰기 연산이 병렬적으로 발생하기 때문에 일관성이 깨질 수 있는데, 이 문제는 클라이언트단에서 해결해야 함 &amp;rarr; 해소 방법: 데이터 버저닝&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;비 일관성 해소 기법: 데이터 버저닝&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;버저닝(versioning) 과 벡터 시계(vector clock) 로 문제 해소 가능&lt;/li&gt;
&lt;li&gt;버저닝: 데이터를 변경할 때마다 해당 데이터의 새로운 버전을 만드는 것을 의미. 각 버전의 데이터는 변경 불가능&lt;/li&gt;
&lt;li&gt;데이터 일관성이 깨지는 예시&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (3).png&quot; data-origin-width=&quot;514&quot; data-origin-height=&quot;253&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bu83as/dJMcahQeEYG/Rn0akR4taygEtcOxMAIh2k/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bu83as/dJMcahQeEYG/Rn0akR4taygEtcOxMAIh2k/img.png&quot; data-alt=&quot;데이터 일관성이 깨지지 않을 때&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bu83as/dJMcahQeEYG/Rn0akR4taygEtcOxMAIh2k/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fbu83as%2FdJMcahQeEYG%2FRn0akR4taygEtcOxMAIh2k%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;514&quot; height=&quot;253&quot; data-filename=&quot;제목 없는 다이어그램 (3).png&quot; data-origin-width=&quot;514&quot; data-origin-height=&quot;253&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;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (4).png&quot; data-origin-width=&quot;570&quot; data-origin-height=&quot;237&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dIEFcg/dJMcaklTdI6/UW8AgvdvdOKI4IU0EQ0nY0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dIEFcg/dJMcaklTdI6/UW8AgvdvdOKI4IU0EQ0nY0/img.png&quot; data-alt=&quot;두 연산이 각각 서버에 동시에 들어왔을 때&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dIEFcg/dJMcaklTdI6/UW8AgvdvdOKI4IU0EQ0nY0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdIEFcg%2FdJMcaklTdI6%2FUW8AgvdvdOKI4IU0EQ0nY0%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;570&quot; height=&quot;237&quot; data-filename=&quot;제목 없는 다이어그램 (4).png&quot; data-origin-width=&quot;570&quot; data-origin-height=&quot;237&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;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: left;&quot;&gt;&amp;rarr; 보편적으로, 데이터 일관성 해결을 위해&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;&lt;u&gt;벡터 시계&lt;/u&gt;를 활용하여 문제를 푼다고 함&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;벡터 시계: [서버, 버전] 순서쌍을 데이터에 매단 것&lt;/li&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;동일한 데이터에 대해 서버 별로 벡터시계 기록 (ex. D([서버 X, 3], [서버 Y, 1], [서버 Z, 1]))&lt;/li&gt;
&lt;/ul&gt;
&lt;li&gt;버전 사이의 충돌 감지 방법
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;D(&lt;b&gt;[서버0, 1], [서버1, 1]&lt;/b&gt;) 과 D(&lt;b&gt;[서버0, 1], [서버1, 2]&lt;/b&gt;) : 충돌이 아님. 후자가 더 상위버전&lt;/li&gt;
&lt;li&gt;D(&lt;b&gt;[서버0, 2], [서버1, 1]&lt;/b&gt;) 과 D(&lt;b&gt;[서버0, 1], [서버1, 2]&lt;/b&gt;) : 충돌&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;벡터 시계 사용하여 충돌을 감지하고 해소하는 방법의 단점
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;충돌 감지 및 해소 로직이 클라이언트에 들어가야 하므로, 클라이언트 구현이 복잡해짐&lt;/li&gt;
&lt;li&gt;[서버 : 버전] 의 순서쌍 개수가 굉장히 빨리 늘어남 &amp;rarr; 임계치(threshold) 설정하여 오래된 순서쌍 제거하도록 하기(해당 방법은 아마존 실서비스에서 크게 문제된 적은 없었다고 함)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;장애 처리&lt;/h3&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;장애 감지 (failure detection)&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;일반적으로,&amp;nbsp;멀티캐스팅(multicasting)&amp;nbsp;채널을 구축하여, 서버 두 대 이상이 장애를 감지하면, 장애 발생했다고 간주 &amp;rarr; 그러나, 서버가 많을 때 해당 방법은 비효율적&lt;/li&gt;
&lt;li&gt;&lt;span style=&quot;background-color: #9feec3;&quot;&gt;가십 프로토콜(gossip protocol)&lt;/span&gt;&amp;nbsp;같은 분산형 장애 감지(decentralized failure detection) 솔루션이 더 효율적
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;(1) 각 노드는 멤버십 목록을 유지. 멤버십 목록은 각 멤버ID-heartbeat_counter 쌍의 목록임&lt;/li&gt;
&lt;li&gt;(2) 각 노드는 주기적으로 자신의 heartbeat_counter 를 증가시킴&lt;/li&gt;
&lt;li&gt;(3) 각 노드는 &lt;span style=&quot;background-color: #9feec3;&quot;&gt;무작위로 선정된 노드들에게&lt;/span&gt; 주기적으로 자기 heartbeat_counter 목록을 보냄 (참고: 다른 자료 확인했을 때, push 시키는 것보다 pull 이 오버헤드가 작다고 함)&lt;/li&gt;
&lt;li&gt;(4) heartbeat_counter 목록을 받은 노드는 멤버십 목록을 최신 값으로 갱신&lt;/li&gt;
&lt;li&gt;(5) 어떤 멤버의 heartbeat_counter 값이 지정된 시간 동안 갱신되지 않으면, 해당 멤버는 장애(offline) 상태인 것으로 간주&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;일시적 장애 처리&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;엄격한 정족수(strict quorum) 접근법을 쓴다면, 장애 발생 시 읽기/쓰기 연산 금지&lt;/li&gt;
&lt;li&gt;느슨한 정족수(sloppy quorum) 접근법은 연산을 수행할 N개의 서버를 해시링에서 골라 연산 수행 &amp;rarr; 가용성을 높임&lt;/li&gt;
&lt;li&gt;장애 서버로 가는 요청은 다른 서버가 잠시 맡아 처리하는데, 이 때 쓰기 연산을 처리한 서버에는 단서(hint) 를 남겨둠.(임시 위탁(hinted handoff) 기법)&lt;span style=&quot;color: #333333; text-align: left;&quot;&gt;&lt;span&gt;&amp;nbsp;&lt;/span&gt;&amp;rarr; &lt;/span&gt;장애 서버 복구 시 일괄 반영하여 일관성 보존&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;영구 장애 처리&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;영구적인 노드 장애의 경우(~=데이터 불일치),&amp;nbsp;&lt;u&gt;안티 엔트로피&lt;/u&gt;&amp;nbsp;프로토콜을 구현하여 사본 동기화
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;안티 엔트로피 프로토콜은 사본들을 비교하여 최신 버전으로 갱신하는 과정을 포함함&lt;/li&gt;
&lt;li&gt;사본 간의 일관성이 망가진 상태를 탐지하고, 전송 데이터의 양을 줄이기 위해&amp;nbsp;&lt;u&gt;머클(Merkle) 트리&lt;/u&gt;&amp;nbsp;사용&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;머클트리(해시트리): 각 노드의 종단 노드에 보관된 값의 해시, 혹은 종단 노드로부터 계산된 해시 값을 레이블로 붙여둔 트리&lt;/li&gt;
&lt;li&gt;예시:&amp;nbsp;키 공간(key space)이 1부터 12까지일 경우, 머클 트리를 만드는 과정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;1단계: 키 공간을 버킷(bucket)으로 나눔 (아래 그림에서는 버킷 4개로 나눔)&amp;nbsp;&lt;br /&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dna/d6MpI9/dJMcac2sH6f/AAAAAAAAAAAAAAAAAAAAAHYwg57C1gPJc49plHnKLOzmMCwB05UsXkJ3Q7LmtMcT/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1761922799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=s37B%2F%2Bbd2GayQ5yciXe029U%2BAXw%3D&quot; data-image-src=&quot;https://blog.kakaocdn.net/dna/d6MpI9/dJMcac2sH6f/AAAAAAAAAAAAAAAAAAAAAHYwg57C1gPJc49plHnKLOzmMCwB05UsXkJ3Q7LmtMcT/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1761922799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=s37B%2F%2Bbd2GayQ5yciXe029U%2BAXw%3D&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;271&quot; data-filename=&quot;제목 없는 다이어그램 (5).png&quot; /&gt;&amp;nbsp;&lt;/li&gt;
&lt;li&gt;2단계: 버킷에 포함된 각각의 키에 균등 분포 해시(uniform hash) 함수를 적용하여 해시 값 계산&lt;br /&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dna/BcBSV/dJMb99YYXlG/AAAAAAAAAAAAAAAAAAAAALIsD-s2xZU34W1j3-GlsDRCj7Q8mFDATmXqTUecxhSx/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=IWeOoW4%2BYQmdz1lsJSVl%2BHeIFDo%3D&quot; data-image-src=&quot;https://blog.kakaocdn.net/dna/BcBSV/dJMb99YYXlG/AAAAAAAAAAAAAAAAAAAAALIsD-s2xZU34W1j3-GlsDRCj7Q8mFDATmXqTUecxhSx/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=IWeOoW4%2BYQmdz1lsJSVl%2BHeIFDo%3D&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;271&quot; data-filename=&quot;제목 없는 다이어그램 (6).png&quot; /&gt;&lt;/li&gt;
&lt;li&gt;3단계: 버킷별로 해시값을 계산한 후, 해당 해시 값을 레이블로 갖는 노드를 만듦&lt;br /&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dna/cCyl28/dJMcafx75RG/AAAAAAAAAAAAAAAAAAAAALlaYXW-YSa2cLnEOEHy4MeH0gDGf_SV6wsTHpI_rnMs/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=Xm%2FDNrG6ecgPPVLoTutyli6gW%2Bc%3D&quot; data-image-src=&quot;https://blog.kakaocdn.net/dna/cCyl28/dJMcafx75RG/AAAAAAAAAAAAAAAAAAAAALlaYXW-YSa2cLnEOEHy4MeH0gDGf_SV6wsTHpI_rnMs/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=Xm%2FDNrG6ecgPPVLoTutyli6gW%2Bc%3D&quot; data-origin-width=&quot;694&quot; data-origin-height=&quot;281&quot; data-filename=&quot;제목 없는 다이어그램 (7).png&quot; /&gt;&lt;/li&gt;
&lt;li&gt;4단계: 자식 노드의 레이블로부터 새로운 해시 값을 계산하여, 이진 트리를 상향식(bottom-up)으로 구성해나감&lt;br /&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dna/bktky3/dJMcaiBCz3A/AAAAAAAAAAAAAAAAAAAAAHfCbgTxOvKGSs--NnegmbfPf77AxC2haAR5G2QrHiSI/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=0fgMozRojSHIFVIFUWc8BTLllnw%3D&quot; data-image-src=&quot;https://blog.kakaocdn.net/dna/bktky3/dJMcaiBCz3A/AAAAAAAAAAAAAAAAAAAAAHfCbgTxOvKGSs--NnegmbfPf77AxC2haAR5G2QrHiSI/img.png?credential=yqXZFxpELC7KVnFOS48ylbz2pIh7yKj8&amp;amp;expires=1764514799&amp;amp;allow_ip=&amp;amp;allow_referer=&amp;amp;signature=0fgMozRojSHIFVIFUWc8BTLllnw%3D&quot; data-origin-width=&quot;694&quot; data-origin-height=&quot;421&quot; data-filename=&quot;제목 없는 다이어그램 (8).png&quot; /&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;위와 같이 루트 노드의 해시값을 비교하여, 다른 데이터를 갖는 버킷을 찾아 그 버킷만 동기화하면 됨&lt;/li&gt;
&lt;li&gt;버킷 하나에 많은 데이터가 들어갈 수 있으므로, 버킷 하나의 데이터 크기는 꽤 크다는 것을 알아두어야 함. (ex. 전체 key 개수 10억개일 경우, 10만개의 버킷으로 관리하며, 버킷 당 key 1000개씩 관리)&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;데이터 센터 장애 처리&lt;/h4&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;데이터 센터 장애에 대응을 위해 데이터를 여러 데이터 센터에 다중화&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;시스템 아키텍처 다이어그램&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;주된 기능 설명&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;클라이언트는 키-값 저장소가 제공하는 두 가지 단순한 API(get, put)와 통신&lt;/li&gt;
&lt;li&gt;중재자는 클라이언트에게 키-값 저장소에 대한 proxy 역할을 하는 노드&lt;/li&gt;
&lt;li&gt;노드는 안정 해시(consistent hash) 의 해시 링(hash ring) 위에 분포&lt;/li&gt;
&lt;li&gt;노드를 자동으로 추가 또는 삭제할 수 있도록, 시스템은 완전히 분산되어야 함&lt;/li&gt;
&lt;li&gt;데이터는 여러 노드에 다중화&lt;/li&gt;
&lt;li&gt;모든 노드가 같은 책임을 지므로, SPOF(Single Point of Failure)는 존재하지 않는다&lt;/li&gt;
&lt;li&gt;모든 노드들은 앞서 이야기했던 장애 감지, 데이터 불일치 해소, 다중화 등의 모든 기능들이 전부 지원되어야 함&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;쓰기 경로&lt;/h3&gt;
&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;521&quot; data-origin-height=&quot;331&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/kRKyx/dJMcaaQ7Klf/G6tW9d32uMtUYa9kXuRHk0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/kRKyx/dJMcaaQ7Klf/G6tW9d32uMtUYa9kXuRHk0/img.png&quot; data-alt=&quot;카산드라(Cassandra)의 예시&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/kRKyx/dJMcaaQ7Klf/G6tW9d32uMtUYa9kXuRHk0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FkRKyx%2FdJMcaaQ7Klf%2FG6tW9d32uMtUYa9kXuRHk0%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;662&quot; height=&quot;421&quot; data-filename=&quot;제목 없는 다이어그램.png&quot; data-origin-width=&quot;521&quot; data-origin-height=&quot;331&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;카산드라(Cassandra)의 예시&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;ol style=&quot;list-style-type: decimal;&quot; data-ke-list-type=&quot;decimal&quot;&gt;
&lt;li&gt;쓰기 요청이 커밋 로그(commit log) 파일에 기록됨&lt;/li&gt;
&lt;li&gt;데이터가 메모리 캐시에 기록됨&lt;/li&gt;
&lt;li&gt;메모리 캐시가 가득차거나 사전에 정의된 어떤 임계치에 도달하면 데이터는 디스크에 있는 SSTable에 기록됨SSTable: Sorted-String Table, &amp;lt;키, 값&amp;gt; 순서쌍을 정렬된 리스트 형태로 관리하는 테이블&lt;/li&gt;
&lt;/ol&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;읽기 경로&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;SSTable에 데이터가 있는지 없는지를 조회하기 위해, 주로&amp;nbsp;&lt;b&gt;블룸 필터(bloom filter)&lt;/b&gt;&amp;nbsp;를 사용
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;블룸 필터: boolean 형태의 테이블로, 값의 존재여부를 검사할 수 있는 데이터 구조&lt;/li&gt;
&lt;li&gt;정확하게 &quot;없다&quot;를 말할 수는 있지만, 정확하게 &quot;있다&quot;를 말할 수는 없음 (해시 충돌 발생으로 인해 있다고 판단될 수 있기 때문에)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;591&quot; data-origin-height=&quot;331&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/mIFDJ/dJMcabCuOBW/oDgduDtIoowrmcvUfkpi1k/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/mIFDJ/dJMcabCuOBW/oDgduDtIoowrmcvUfkpi1k/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/mIFDJ/dJMcabCuOBW/oDgduDtIoowrmcvUfkpi1k/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FmIFDJ%2FdJMcabCuOBW%2FoDgduDtIoowrmcvUfkpi1k%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;706&quot; height=&quot;395&quot; data-filename=&quot;제목 없는 다이어그램 (1).png&quot; data-origin-width=&quot;591&quot; data-origin-height=&quot;331&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;ol style=&quot;list-style-type: decimal;&quot; data-ke-list-type=&quot;decimal&quot;&gt;
&lt;li&gt;데이터가 메모리에 있는지 검사. 없다면 2번으로&lt;/li&gt;
&lt;li&gt;데이터가 메모리에 없으므로 블룸 필터(bloom filter)를 검사&lt;/li&gt;
&lt;li&gt;블룸 필터를 통해 어떤 SSTable에 키가 보관되어 있는지 알아냄&lt;/li&gt;
&lt;li&gt;SSTable에서 데이터를 가져옴&lt;/li&gt;
&lt;li&gt;해당 데이터를 클라이언트에 반환&lt;/li&gt;
&lt;/ol&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size14&quot;&gt;출처: 가상 면접 사례로 배우는 대규모 시스템 설계 기초(알렉스 쉬 저자, 이병준 번역)&lt;/p&gt;</description>
      <category>도서/대규모시스템설계기초1</category>
      <category>대규모시스템설계</category>
      <category>저장소설계</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/31</guid>
      <comments>https://hyewon-s-dev.tistory.com/31#entry31comment</comments>
      <pubDate>Mon, 3 Nov 2025 14:05:11 +0900</pubDate>
    </item>
    <item>
      <title>리눅스마스터 1급 2차 내용 정리</title>
      <link>https://hyewon-s-dev.tistory.com/30</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;&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;&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;&amp;nbsp;&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;기본적인 경로&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/var/log 하위 --&amp;gt; 로그 관련 폴더들 존재 (wtmp, btmp, syslog(message) 등)&lt;/li&gt;
&lt;li&gt;설정(conf) 파일들 --&amp;gt; /etc/{패키지명} 하위&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;iptables filter&lt;/h2&gt;
&lt;table style=&quot;border-collapse: collapse; width: 65.2324%; height: 57px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 17.7907%;&quot;&gt;Filter&lt;/td&gt;
&lt;td style=&quot;width: 44.305%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 17.7907%; height: 19px;&quot;&gt;INPUT&lt;/td&gt;
&lt;td style=&quot;width: 44.305%; height: 19px;&quot;&gt;목적지가 localhost. 유입되는 패킷 필터링&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 17.7907%; height: 19px;&quot;&gt;OUTPUT&lt;/td&gt;
&lt;td style=&quot;width: 44.305%; height: 19px;&quot;&gt;출발지가 localhost. 나가는 패킷 필터링&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 17.7907%; height: 19px;&quot;&gt;FORWARD&lt;/td&gt;
&lt;td style=&quot;width: 44.305%; height: 19px;&quot;&gt;라우터&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;`iptables -A INPUT -s 192.168.10.7 -d localhost -j DROP`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: INPUT 체인에서 source 주소가 192.168.10.7이고, 목적지 주소가 localhost 인 패킷 거부&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;`iptables -A INPUT -s 192.168.10.7 -p icmp -j REJECT`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: INPUT 체인에서 소스 주소가 &lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;192.168.10.7&lt;span&gt; 인 ICMP(프로토콜) 패킷을 거부하며 대상 호스트에 메시지 전달&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A INPUT -s 192.168.10.0/24 ! -p icmp -j ACCEPT`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: INPUT 체인에서 소스 주소가 192.168.10.0 대역이고, ICMP 패킷이 아닌 경우, 모든 패킷을 허용한다.&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A OUTPUT -p tcp -d www.test.com --dport 80 -o eth0 -j DROP`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: www.test.com 에 접속하는 것을 차단하기 위해&amp;nbsp;&amp;nbsp;&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -L INPUT --line-numbers`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: INPUT 체인에 설정된 정책을 번호와 함께 출력&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -D INPUT 3`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: INPUT 체인의 3번째 정책 제거&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -P INPUT DROP`&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A INPUT -s 192.168.10.7 -j ACCEPT`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: 기본 설정으로 들어오는 모든 패킷을 거부하게 하고, 192.168.10.7 에서 오는 패킷만 허용&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A INPUT -p tcp --dport 80 -j ACCEPT`&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A INPUT -p tcp --dport 10:100 -j DROP`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: 들어오는 패킷 중 TCP 포트번호가 10번 ~ 100번인 것을 거부하나, HTTP 서비스를 위한 80 포트는 허용. &lt;b&gt;만일, 중복된 정책이 있을 경우, 먼저 등록된 정책이 적용됨.&lt;/b&gt;&lt;/span&gt;&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;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;`iptables -A INPUT -p tcp --dport 80 -syn -m limit --limit 100/s -j ACCEPT`&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;&lt;span&gt;: 초당 허용 접속 개수를 제한하여 TCP flooding 공격에 대응&lt;/span&gt;&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;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size26&quot;&gt;iptables 설정 정책 저장 및 자동 적용&lt;/h2&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 44.8837%;&quot;&gt;명령어&lt;/td&gt;
&lt;td style=&quot;width: 55.1163%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 44.8837%;&quot;&gt;iptables-save &amp;gt; firewall.sh&lt;/td&gt;
&lt;td style=&quot;width: 55.1163%;&quot;&gt;현재 설정되어있는 iptables 의 rule을 firewall.sh 파일로 저장&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 44.8837%;&quot;&gt;iptables-restore &amp;lt; firewall.sh&lt;/td&gt;
&lt;td style=&quot;width: 55.1163%;&quot;&gt;firewall.sh 파일에 저장되어있는 iptables 의 rule을 불러와 반영&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 44.8837%;&quot;&gt;service iptables save&lt;/td&gt;
&lt;td style=&quot;width: 55.1163%;&quot;&gt;/etc/sysconfig/iptables 에 정책 저장&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&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;h2 style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size26&quot;&gt;iptables NAT&lt;/h2&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 18.2558%;&quot;&gt;-j 옵션&lt;/td&gt;
&lt;td style=&quot;width: 81.7442%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 18.2558%;&quot;&gt;SNAT&lt;/td&gt;
&lt;td style=&quot;width: 81.7442%;&quot;&gt;공인 IP 주소 하나를 다수의 호스트가 공유하여 인터넷을 사용할 수 있게 됨 (소스 IP 주소 변경)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 18.2558%;&quot;&gt;DNAT&lt;/td&gt;
&lt;td style=&quot;width: 81.7442%;&quot;&gt;하나의 공인 IP 로 여러 개의 서버에 접속할 수 있도록 구성 가능 (목적지 IP 주소 변경)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;table style=&quot;border-collapse: collapse; width: 61.0465%; height: 57px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 36.4308%; height: 19px;&quot;&gt;-j 옵션 - -A 옵션&lt;/td&gt;
&lt;td style=&quot;width: 20.9452%; height: 19px;&quot;&gt;패킷 이동경로&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 36.4308%; height: 19px;&quot;&gt;SNAT - POSTROUTING&lt;/td&gt;
&lt;td style=&quot;width: 20.9452%; height: 19px;&quot;&gt;내부 &amp;rarr; 외부&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 36.4308%; height: 19px;&quot;&gt;DNAT - PREROUTING&lt;/td&gt;
&lt;td style=&quot;width: 20.9452%; height: 19px;&quot;&gt;외부 &amp;rarr; 내부&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;`iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to 222.235.10.7`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: 첫 번째 이더넷 카드(eth0)를 통해 외부로 나가는 패킷에 222.235.10.7 IP 주소 부여&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;`iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to 222.235.10.7-222.234.10.25`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: IP 대역(범위)를 지정하여 소스 주소 변경 가능&lt;br /&gt;: 첫 번째 이더넷 카드(eth0)를 통해 외부로 나가는 패킷은 222.235.10.7 ~ 222.234.10.25 사이의 ip 대역으로 부여&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;`iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to MASQUERADE`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: masquerade 는 유동 IP 주소로 소스 주소를 변경할 수 있음&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;`iptables -t nat -A PREROUTING -p tcp -d 222.235.10.7 --dport 80 -j DNAT --to 192.168.10.7:80`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: 222.235.10.7 의 80번 포트로 들어오는 패킷을 192.168.10.7 의 80 포트로 연결&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;`iptables -t nat -A PREROUTING -i eth1 -p tcp --dport 80 -j REDIRECT --to-port 8080`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: eth1 네트워크 인터페이스로 수신되는 모든 패킷을 대상으로 하며(-i eth1), 웹 브라우저의 프록시 옵션을 설정하지 않고, 네트워크 상에서 투명하게 동작하는 '투명 프록시'를 설정(-j REDIRECT)&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;[참고] 리눅스에서 NAT 사용을 위한 설정 값&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- /proc/sys/net/ipv4/ip_forward 값이 1로 설정되어야 함&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;h2 data-ke-size=&quot;size26&quot;&gt;DHCP (dhcpd.conf)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;range: 클라이언트에 할당할 IP 범위를 지정한다.
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `range 239.252.197.10 239.252.197.250;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;range dynamic-bootp: DHCP 클라이언트와 BOOTP 클라이언트를 함께 지원한다.&lt;/li&gt;
&lt;li&gt;option domain-name: 도메인 이름 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `option domain-name &quot;kait.or.kr&quot;;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;option domain-name-servers: 네임 서버 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `option domain-name-servers 192.168.5.13;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;option routers: 게이트웨이 주소 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `option routers 192.168.12.1;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;option broadcast-address: 브로드캐스팅 주소 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `option broadcast-address 192.168.12.255;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;default-lease-time: 초(sec) 단위로 임대요청 만료시간 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `default-lease-time 7200;`&lt;/li&gt;
&lt;li&gt;7200: 2시간, 14400: 4시간&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;max-lease-time: 초 단위로 클라이언트가 사용할 IP 의 최대 시간 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `max-lease-time 14400;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;option subnet-mask: 서브넷 마스크 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `option subnet-mask 255.255.255.0;`&amp;nbsp; &amp;nbsp; &amp;nbsp;(하나의 네트워크만 운영 가능)&lt;/li&gt;
&lt;li&gt;ex. `option subnet-mask 255.255.255.192;`&amp;nbsp; &amp;nbsp; (4개의 서브넷으로 나누어 운영)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;fixed-address: 특정 MAC 주소를 갖는 시스템(hardware ethernet) 에 고정적인 IP 주소 할당&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;[참고] 만일 DHCP의 로그 메시지를 다른 곳으로 전달하고 싶다면 --&amp;gt; log-facility 항목 사용&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- ex. `log-facility local7;`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2 data-ke-size=&quot;size26&quot;&gt;Squid (프록시 서버, squid.conf)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;cache_dir: 캐시 데이터가 저장된 경로명 저장
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `cache_dir nfs /var/spool/squid 100 16 256`&lt;/li&gt;
&lt;li&gt;cache_dir nfs {경로} {캐시데이터 크기, MB} {첫 번째 디렉터리 수} {두 번째 디렉터리 수}&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;http_port [포트번호]: 사용할 포트번호 정하기&lt;/li&gt;
&lt;li&gt;아래의 문법은 모두 acl 구문으로 별칭 지정하는 문법
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;acl [별칭] src [IP 주소 대역]&lt;/li&gt;
&lt;li&gt;acl [별칭] dst [IP 주소 대역]&lt;/li&gt;
&lt;li&gt;acl [별칭] port [포트번호]&lt;/li&gt;
&lt;li&gt;acl [별칭] srcdomain [도메인명](도메인명 적을 때 앞에 `.` 까먹지말기)&lt;/li&gt;
&lt;li&gt;acl [별칭] dstdomain [도메인명](도메인명 적을 때 앞에 `.` 까먹지말기)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;http_access allow [별칭]: 접근 허가&lt;br /&gt;http_access deny [별칭]: 접근 거부
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `acl local src 192.16810.0/24`&lt;br /&gt;`http_access allow local`&lt;br /&gt;`http_access deny all`&lt;br /&gt;--&amp;gt; local 별칭만 접근 허가하고, 나머지는 거부&lt;/li&gt;
&lt;li&gt;ex. `acl Safe_ports port 80`&lt;br /&gt;`acl Safe_ports port 21`&lt;br /&gt;`http_access deny !Safe_ports`&lt;br /&gt;--&amp;gt; Safe_ports 외에는 모두 거부&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;/etc/named.conf&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;DNS. 서버 프로그램 이름은 bind, 데몬은 named&lt;/li&gt;
&lt;li&gt;/etc/named.conf
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;존(zone) 파일, 리버스 존(Reverse Zone, in-addr.arpa) 파일을 비롯한 DNA 서버의 주요한 환경설정 파일&lt;/li&gt;
&lt;li&gt;리버스 존 파일을 이용하여 IP주소에 대한 도메인 정보 조회 제공&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/var/named
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;루트(root) 도메인 서버의 정보를 담은 named.ca, 사용자가 설정한 zone 파일 등을 저장하는 디렉터리&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;directory: zone 파일의 저장 디렉터리를 설정하며, 반드시 필요한 항목
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `directory &quot;/var/named&quot;;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;dump-file: 정보 갱신 시 저장 파일로 사용할 dump file 의 파일명 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `dump-file &quot;/var/named/data/cache-dump.db&quot;;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;statistics-file: 통계 정보를 저장할 파일 명을 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `statistics-file &quot;/var/named/data/named_stats.txt&quot;;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;memstatistics-file: 메모리 통계 정보를 저장할 파일명 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `memstatistics-file &quot;/var/named/data/named-mem-stats.txt&quot;;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;recursing-file: recursing query 정보를 저장하는 파일 명 지정&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;forward: forwarders 옵션과 함게 사용. only, first 둘 중 하나 (해당 내용은 yum으로 설치 시 conf에 기본적으로 제공됨)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`forward only;`: 도메인 주소에 대한 질의를 다른 서버에 넘김&lt;/li&gt;
&lt;li&gt;`forward first;`: 다른 서버에서 응답이 없을 경우, 자신이 응답하도록 설정&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;forwarders: forward 를 처리할 서버 지정 (DNS 관련 질의를 다른 서버로 넘김) (해당 내용은 yum으로 설치 시 conf에 기본적으로 제공됨)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `forwarders { xxx.xxx.xxx.xxx; yyy.yyy.yyy.yyy; };`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;allow-query: 네임 서버에 질의할 수 있는 호스트 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `allow-query { localhost; };`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;allow-transfer: 존(zone) 파일 내용을 복사(transfer) 할 대상 제한
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `allow-transfer { 172.3.1.0/24; };`&amp;nbsp; &amp;nbsp; (zone 파일로 받을 수 있는 호스트는 172.3.1.0/24 로 설정)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;recurison: 하위 도메인 검색 허용 여부 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `recursion yes;`&lt;/li&gt;
&lt;li&gt;yes 로 설정하면 네임서버에 설정하지 않은 도메인을 질의할 경우, 캐싱 네임서버의 역할로 동작하며 DNS 질의 수행&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;acl 구문: 여러 호스트들을 하나의 이름으로 지정하여(별칭 지정) options 구문의 allow-query, allow-transfer 등에 사용 (단, 해당 acl은 allow-* 구문 이전에 작성해야 함)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `acl &quot;ihd&quot; {192.168.2.24; 192.168.4/24;}`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;/etc/named.rfc1912.zones&lt;/h2&gt;
&lt;table style=&quot;border-collapse: collapse; width: 76.3954%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 23.6971%;&quot;&gt;zone type&lt;/td&gt;
&lt;td style=&quot;width: 51.2314%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 23.6971%;&quot;&gt;hint&lt;/td&gt;
&lt;td style=&quot;width: 51.2314%;&quot;&gt;루트 도메인 지정&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 23.6971%;&quot;&gt;master&lt;/td&gt;
&lt;td style=&quot;width: 51.2314%;&quot;&gt;1차 네임서버 지정&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 23.6971%;&quot;&gt;slave&lt;/td&gt;
&lt;td style=&quot;width: 51.2314%;&quot;&gt;2차 네임서버 지정&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&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;pre id=&quot;code_1761807004891&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# 루트 도메인 예시
zone &quot;.&quot; IN {
    type hint;
    file &quot;named.ca&quot;;
}&lt;/code&gt;&lt;/pre&gt;
&lt;pre id=&quot;code_1761806851354&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# Zone 예시
zone &quot;linux.or.kr&quot; IN {
    type master;
    file &quot;linux.zone&quot;;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;--&amp;gt; 여기서 `file &quot;linux.zone&quot;;` 파일은 /var/named 하위에 있음&lt;/p&gt;
&lt;pre id=&quot;code_1761807076594&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# Reverse Zone 예시
zone &quot;3.109.210.in-addr.arpa&quot; IN {
    type master;
    file &quot;linux.rev&quot;;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;--&amp;gt; 원래 ip 주소: 210.109.3.5&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;h2 data-ke-size=&quot;size26&quot;&gt;/var/named 아래 (&quot;도메인명.zone&quot; or &quot;도메인명&quot;.rev)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;주석: `;`(세미콜론)&lt;/li&gt;
&lt;li&gt;⭐ 도메인명 맨 뒤에 무조건 `.` 붙이기&lt;/li&gt;
&lt;li&gt;`$ TTL 1D`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;설정한 정보를 다른 DNS 서버에서 조회하였을 경우, 캐시에 보관할 시간&lt;/li&gt;
&lt;li&gt;ZONE 파일의 첫 번째 라인에 위치해야 함&lt;/li&gt;
&lt;li&gt;기본 단위는 초. W, D, M 단위로 저장 가능&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;SOA 레코드 (Start Of Authority)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;도메인 관리자 메일, 일련 번호 등 DNS 핵심 정보 지정&lt;/li&gt;
&lt;li&gt;`@` 기호는 오리진(origin) 도메인을 의미하며, /etc/named.conf 파일에서 설정한 도메인명임.&lt;br /&gt;만일, 도메인 이름을 직접 지정할 경우, 마지막에 `.` 을 반드시 추가해야 함&lt;/li&gt;
&lt;li&gt;ex. `@&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; SOA&amp;nbsp; &amp;nbsp; ns.ihd.or.kr.&amp;nbsp; &amp;nbsp; kait.ihd.or.kr.`&lt;br /&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`ns.ihd.or.kr.`: mname. 도메인 존의 마스터 네임서버 도메인 이름&lt;/li&gt;
&lt;li&gt;`kait.ihd.or.kr.`: rname. 도메인 존을 관리하는 담당자의 연락처를 도메인 이름으로 설정&lt;br /&gt;만일 rname 부분이 `admin@example.com` 이 담당자일 경우, `admin.example.com.` 으로 작성하면 됨.&lt;/li&gt;
&lt;li&gt;rname 부분은 `.` 만 입력하여 필드 네임 비워두는 것도 가능함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;시험 중, 이 레코드 대략적으로 확인해볼 수 있는 명령어
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `dig&amp;nbsp;naver.com&amp;nbsp;soa&amp;nbsp;+multi`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;serial: Zone 파일이 갱신되면 증가하게 되는 일련번호. 날짜형식&lt;br /&gt;갱신된 최신 데이터인지 판단하는 &quot;유일한 기준&quot;&lt;/li&gt;
&lt;li&gt;refresh: 주 네임서버 접근 주기 지정. 도메인 존의 데이터 변경 여부 체크&lt;/li&gt;
&lt;li&gt;retry: refresh 실패할 경우 다시 시도하는 주기 (재시도할 주기)&lt;/li&gt;
&lt;li&gt;expire: retry 수차례 반복 후 실패 시 폐기하여 서비스 중단처리하는 최대 기간&lt;/li&gt;
&lt;li&gt;minimum: 정보 최소 보관 시간&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;refresh, retry, expire 는 &quot;데이터 동기화&quot; 가 목적임&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;레코드 추가 예시&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;`&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; NS&amp;nbsp; &amp;nbsp; ns.ihd.or.kr.`&amp;nbsp; &amp;nbsp; (IN 생략 가능. 첫 번째 필드는 도메인명으로, &lt;span style=&quot;color: #ef5369;&quot;&gt;&lt;b&gt;필드 공백 반드시 필요&lt;/b&gt;&lt;/span&gt;)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: 네임서버는 ns.ihd.or.kr 사용&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; IN&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp; 192.168.12.22`&amp;nbsp; &amp;nbsp; &lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;(IN 생략 가능.&lt;span style=&quot;color: #ef5369;&quot;&gt; &lt;b&gt;첫 번째&amp;nbsp;&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;color: #ef5369;&quot;&gt;&lt;b&gt;필드 공백 반드시 필요&lt;/b&gt;&lt;/span&gt;)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: IP 주소와 도메인 매핑&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; IN&amp;nbsp; &amp;nbsp; MX&amp;nbsp; &amp;nbsp; 10&amp;nbsp; &amp;nbsp; ihd.or.kr.`&amp;nbsp; &amp;nbsp; &lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;(IN 생략 가능.&lt;span style=&quot;color: #ef5369;&quot;&gt; &lt;b&gt;첫 번째&amp;nbsp;&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;color: #ef5369;&quot;&gt;&lt;b&gt;필드 공백 반드시 필요&lt;/b&gt;&lt;/span&gt;)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: 도메인 이름에 대한 메일 교환서버(ihd.or.kr) 알려줌&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;`15&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; PTR&amp;nbsp; &amp;nbsp; ihd.or.kr.`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: IP 주소10.0.2.15 일 때, 해당 IP 주소를 조회하면 ihd.or.kr 이 나타나도록 설정&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: 여기서 만약 PTR 레코드 부분이 A 나 AAAA 의 경우, 이는 정방향 DNS&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;`www&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp; 192.168.5.13`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: www 도메인을 사용하는 호스트의 IP 주소를 192.168.5.13 으로 설정&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;`www1&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; CNAME&amp;nbsp; &amp;nbsp; www`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;: www1 도메인을 www 와 매핑&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;첫 번째 필드가 공백인 경우, @(origin) 도메인을 생략하는 대신인 것 같음.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;만약, @ 가 example.com. 이라 할 때,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;`@&amp;nbsp; &amp;nbsp; IN&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp;192.168.5.13`&amp;nbsp; ==&amp;nbsp; `example.com.&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp; 192.168.5.13`&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;`ns&amp;nbsp; &amp;nbsp;IN&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp;192.168.5.13`&amp;nbsp; ==&amp;nbsp; `ns.example.com.&amp;nbsp; &amp;nbsp; A&amp;nbsp; &amp;nbsp; 192.168.5.13`&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;h2 data-ke-size=&quot;size26&quot;&gt;메일관련 / sendmail&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/aliases&amp;nbsp; --&amp;gt;&amp;nbsp; `newaliases` or `sendmail -bi`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;별칭, 특정 계정으로 수신한 메일을 다른 계정으로 전달하도록 설정&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/mail/local-host-names
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;메일 서버에서 사용하는 도메인(ex. ihd.or.kr) 등록. sendmail 재시작 필요&lt;/li&gt;
&lt;li&gt;cf. domaintable: 도메인 별칭 등록&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/mail/sendmail.cf&amp;nbsp; --&amp;gt;&amp;nbsp; `m4 sendmail.mc &amp;gt; sendmail.cf`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;sendmail 의 기본(main) 설정 파일&lt;/li&gt;
&lt;li&gt;&amp;gt; 방향 잘 기억해두기&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/mail/access --&amp;gt; `makemap hash /etc/mail/access &amp;lt; /etc/mail/access`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;메일 서버에 접속하는 호스트의 접근을 제어하는 설정파일&lt;/li&gt;
&lt;li&gt;`From: spam.com&amp;nbsp; &amp;nbsp; REJECT`: spam.com 으로부터 오는 메일은 &lt;u&gt;거부 후 메시지 전송&lt;/u&gt;&lt;/li&gt;
&lt;li&gt;`From: spam.com&amp;nbsp; &amp;nbsp; DISCARD`: spam.com 으로부터 오는 메일은 &lt;u&gt;그냥 거절&lt;/u&gt;&lt;/li&gt;
&lt;li&gt;`From: spam.com&amp;nbsp; &amp;nbsp; OK`: spam.com 으로부터 오는 메일은 &lt;u&gt;DNS 조회 실패 시에도 허용 (조건 없음)&lt;/u&gt;&lt;/li&gt;
&lt;li&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;RELAY`: host 에 지정된 메일의 수신/발신을 허용&lt;/li&gt;
&lt;li&gt;`To: vip@yourdomain.com&amp;nbsp; &amp;nbsp; REJECT`: 외부에서 vip@yourdomain.com 으로 오는 메일 거부&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/mail/virtusertable --&amp;gt; `makemap hash /etc/mail/virtusertable &amp;lt; /etc/mail/virtusertable`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;특정 도메인의 특정 계정으로 들어온 메일을 어디로 전달할지 지정&lt;/li&gt;
&lt;li&gt;ex. `webmaster@linux.com&amp;nbsp; &amp;nbsp; ihduser`: webmaster@linux.com 으로 들어온 걸 ihduser에게 전달(webmaster@ --&amp;gt; ihduser)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;/etc/mail/sendmail.cf&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;Cwlocalhost: 메일 수신 호스트의 이름 설정(주로 도메인명 이용), 도메인 여러 개일 경우 Fw 사용&lt;/li&gt;
&lt;li&gt;Fw/etc/mail/local-host-names&lt;/li&gt;
&lt;li&gt;Djyoungjin-mail.com
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;메일 발송 시 발신 도메인 이름을 강제 지정 (발신 도메인을 무조건 youngjin-mail.com 으로 설정)&lt;/li&gt;
&lt;li&gt;발신 도메인의 이름은 일반적으로 sendmail 이 자동적으로 결정하므로, 특별한 경우에만 사용함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;~/.forward: 사용자 개인이 수신한 메일을 다른 메일로 포워딩(forwarding) 할 때 설정하는 파일로, 원하는 메일 주소를 한 줄씩 추가&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;httpd/apache (httpd.conf)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;httpd 옵션
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`httpd -t`: httpd.conf 의 문법적 오류 점검&lt;/li&gt;
&lt;li&gt;`httpd -M`: 로딩된 모든 모듈의 목록 출력&lt;/li&gt;
&lt;li&gt;`httpd -L`: 설정 가능한 지시자 확인&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&amp;nbsp;/etc/httpd/conf/httpd.conf
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;LoadModule: DSO(Dynamic Shared Object) 방식으로 로딩할 모듈 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `LoadModule&amp;nbsp; &amp;nbsp; php5_module modules/libphp5.so`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;ServerAdmin: 아파치 웹 서버 관리자의 이메일 주소 지정, 서버에 문제 발생 시 에러메시지 함께 표시
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;default) `ServerAdmin&amp;nbsp; &amp;nbsp; root@localhost`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;ServerName: 서버의 호스트이름 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;default) `ServerName&amp;nbsp; &amp;nbsp; www.example.com:80`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;DocumentRoot: 웹 문서가 저장되는 기본 디렉토리 경로
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;default) `DocumentRoot&amp;nbsp; &amp;nbsp; &quot;/var/www/html&quot;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;DirectoryIndex: 웹 디렉터리를 방문할 경우 처음으로 열릴(Open) 파일 목록 정리
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `DirectoryIndex&amp;nbsp; &amp;nbsp; &amp;nbsp; index.html&amp;nbsp; &amp;nbsp;index.htm&amp;nbsp; &amp;nbsp;index.php&amp;nbsp; &amp;nbsp;index.jsp`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;AccessFilename: 각 디렉터리 별 추가 설정을 위해 각각 저장하는 설정 파일 지정(ex. 접근제어(Access Control))
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;default) `AccessFilename&amp;nbsp; &amp;nbsp; .htaccess`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;AddType: 파일 확장자에 대한 MIME 등록. 해당 파일에 대한 처리방식 지정&lt;/li&gt;
&lt;li&gt;Include: 별도의 설정 파일을&amp;nbsp; 포함하며, 기본값은 `Include conf.d/*.conf`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `Include&amp;nbsp; &amp;nbsp; conf.d/http-mpm.conf`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&amp;lt;Directory /var/www/html&amp;gt;&amp;lt;/Directory&amp;gt;&lt;br /&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;AllowOverride `ALL`: AccessFileName으로 설정한 파일 이용&lt;/li&gt;
&lt;li&gt;AllowOverride `AuthConfig`: AccessFileNmae에 저장된 파일에 대하여 사용자 인증지시자 사용 허락
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;AuthDBFroupFile, AuthDBMUserFile, AuthGroupFile, AuthName, AuthType, AuthUserFile, Require 등과 같은 지시자가 있음 (.htaccess 파일에서 확인)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1761810978428&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# httpd.conf 예시
LoadModule	userdir_module	modules/mod_userdir.so		# 아파치 시작 시 해당 모듈 실행
Include	conf/extra/httpd-userdir.conf					# 설정파일 포함&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/usr/local/apache/conf/extra/httpd-userdir.conf
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`Userdir&amp;nbsp; &amp;nbsp; public_html`&lt;/li&gt;
&lt;li&gt;`Userdir&amp;nbsp; &amp;nbsp; enabled(disabled)&amp;nbsp; &amp;nbsp; john`&amp;nbsp; &amp;nbsp; (john --&amp;gt; 사용자 이름)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;재시작: `/user/local/apache/bin/apachectl restart`&lt;/li&gt;
&lt;li&gt;.htaccess
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;AllowOverride AuthConfig 로 설정해줘야 함&lt;/li&gt;
&lt;li&gt;AuthName: 웹 브라우저의 인증창에 표시될 이름(메시지)을 설정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `AuthName &quot;Master Login&quot;`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;AuthUserFile: 사용자 계정 파일
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `AuthUserFile /etc/password`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Require: 접속을 허가할 사용자 지정
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. `Require valid-user`: 사용자 계정 파일에 등록된 사용자 모두를 허가함&lt;/li&gt;
&lt;li&gt;`Require [사용자명, 사용자명, ...]`: 특정 사용자 계정만 허가&lt;/li&gt;
&lt;li&gt;AuthType: Basic, Digest 방식의 인증 방식 지정&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;Samba&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;samba.conf.example 에서 기본 제공되는 항목들이 있으나, 없는 것도 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1761811697741&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[www]  # 윈도우에서 접근할 때 표시되는 폴더 이름을 www로 설정한다
# 간단한 설명
comment = Web Directory

# 공유 디렉토리 경로는 /usr/local/apache/htdocs
path = /usr/local/apache/htdocs

# 접근 가능한 사용자는 ihduser, kaituser 만 가능하며, 두 사용자 모두 파일 생성 및 삭제 권한 부여
valid users = ihduser kaituser
writable = yes
# (or) write list = ihduser kaituser
# 그룹으로 지정 시 @ 사용. ex) @manager

# 접속 시 사용할 이름 지정. 윈도우 운영체제에서 이름으로 접근할 때의 명칭
netbios name = ihd_com

# 공유 그룹명
workgroup = IHD

# 서버에 대한 설명
server string = IHD Server

# 접근할 수 있는 호스트는 192.168.5.0 네트워크 대역에 속한 모든 호스트들과, 로컬시스템 으로 제한
hosts allow = 127. 192.168.5&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;[참고] 127.0.0.0/8 대역은 호스트 &lt;u&gt;내부 사용 용도&lt;/u&gt;로 예약되어 있음. &quot;로컬시스템&quot;&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;h2 data-ke-size=&quot;size26&quot;&gt;NFS (/etc/exports)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/exports
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`/home/share&amp;nbsp; &amp;nbsp; 172.30.1.0/24 (rw, no_root_square)`&lt;/li&gt;
&lt;li&gt;`ro`: 읽기 전용으로 지정(기본값)&lt;/li&gt;
&lt;li&gt;`rw`: 읽기 및 쓰기로 지정&lt;/li&gt;
&lt;li&gt;`async`: 데이터 변경을 기록할 때 비동기적으로 처리&lt;/li&gt;
&lt;li&gt;`sync`: 데이터 변경을 기록할 때 동기적으로 처리. 변경사항이 기록된 후 응답(기본값)&lt;/li&gt;
&lt;li&gt;`secure`: 포트번호 1024 이하의 요청만 허가(기본값)&lt;/li&gt;
&lt;li&gt;`no_root_squash`: root 접근을 허용&lt;/li&gt;
&lt;li&gt;`root_squash`: root 접근을 거부하기 위하여 클라이언트의 root 요청을 nobody로 맵핑(기본값)&lt;/li&gt;
&lt;li&gt;`all_squash`: NFS에서 접근하는 모든 사용자(root 포함)의 권한을 nobodyfh aovld&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;exportfs
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `exportfs -v`: nfs 서버에서 외부에 공유된 내용을 세부적인 설정 정보를 포함하여 자세히 출력&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;showmount
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `showmount -e 192.168.12.22`: nfs 클라이언트에서 nfs 서버인 192.168.12.22 의 공유된 정보 확인&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;nfsstat: nfs 서버 or nfs 클라이언트에서 nfs 관련 상태정보 출력&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;FTP (/var/vsftpd/vsftpd.conf)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/vsftpd/vsftpd.conf: vsftpd 의 주 설정파일 (man 으로 항목 조회 가능)
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`anonymous_enable=YES`: 익명(anonymous) 사용자의 접속 허용&lt;/li&gt;
&lt;li&gt;`allow_writeable_chroot=YES`: 자신의 홈 디렉터리(chroot jail) 내에서 쓰기 작업을 할 수 있도록 허용&lt;/li&gt;
&lt;li&gt;`chroot_local_user=YES`: 접속한 사용자의 홈 디렉터리를 최상위 디렉터리가 되도록 규정&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/pam.d/vsftpd: vsftpd 의 PAM(Pluggable Authentication Module) 설정 파일&lt;/li&gt;
&lt;li&gt;/etc/vsftpd/ftpusers: PAM 과 연관된 설정파일로, FTP 서비스에 접근할 수 &lt;u&gt;&lt;b&gt;없는&lt;/b&gt;&lt;/u&gt; 사용자(계정) 지정&lt;/li&gt;
&lt;li&gt;/etc/vsftpd/user_list: ftpusers 랑 기능은 유사하나, 주 설정파일인 vsftpd.conf 의 내용에 따라 다르게 동작함&lt;br /&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`userlist_enable=YES` : user_list 사용(기본값)&lt;/li&gt;
&lt;li&gt;`userlist_deny=NO`: user_list 에 있는 사용자 FTP 서비스 사용 가능&lt;/li&gt;
&lt;li&gt;`userlist_deny=YES`: user_list 에 있는 사용자 FTP 서비스 사용 불가능(기본값)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;백업 (backup)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;dump
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`xfsdump -l 0 -f home.xdump /home`: /home 디렉터리 전체를 home.xdump 장치에 백업&lt;br /&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`-l 0`: 0은 백업 전체, 1 ~9 순으로 백업 정도를 나타냄&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;dd
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`dd if=/dev/sdb1 of=/dev/sdc1 bs=1k`: /dev/sdb1 장치를 /dev/sdc1 장치로 백업. 블록 크기는 1KB 로 설정&lt;/li&gt;
&lt;li&gt;`dd if=/dev/zero of=/swap_file count=1024000`: 스왑 파일명은 /swap_file, 스왑 파일 크기 1G&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;restore
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`xfsrestore -rf home.xdump /home`: home.xdump 파일 복원&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;cpio&lt;/li&gt;
&lt;li&gt;async&lt;/li&gt;
&lt;/ul&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;h2 style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size26&quot;&gt;디스크 쿼터(quota)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/fstab: 파일시스템 info. 아래는 해당 파일 기반의 정보를 볼 수 있는 명령어들
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;blkid: UUID 정보 출력
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `blkid /dev/vda1`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;dumpe2fs: 블록사이즈 출력
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex) `dump2fs /dev/vda1`&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;mount&lt;/li&gt;
&lt;li&gt;mke2fs: 파일시스템 생성&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;mkswap&lt;/li&gt;
&lt;li&gt;swapon/swapoff&lt;/li&gt;
&lt;/ul&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;quota: 파일 시스템의 &lt;u&gt;디스크 공간&lt;/u&gt; 또는 &lt;u&gt;파일 개수&lt;/u&gt;에 대한 사용량 제한 --&amp;gt; `/etc/fstab`&lt;/li&gt;
&lt;li&gt;/etc/fstab 파일에서 /home 관련된 영역의 4번째 필드에 추가로 기재해야 할 옵션값: `usrquota`&lt;/li&gt;
&lt;li&gt;`mount -o remount /home`: /home 영역 다시 마운트&lt;/li&gt;
&lt;li&gt;`quotacheck /home`: 파일시스템 체크하여 quota 기록 파일 생성&lt;/li&gt;
&lt;li&gt;`edquota kaituser`: kaituser 사용자에 대한 쿼터 설정&lt;/li&gt;
&lt;li&gt;xfs_quota
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`xfs_quota -x -c &quot;limit bsoft=100m bhard=110m ihduser&quot;`&lt;br /&gt;: ihduser 사용자의 소프트 용량 제한 100MB, 하드 용량 제한 11MB 로 설정&lt;/li&gt;
&lt;li&gt;`xfs_quota -x -c &quot;limit -g bsoft=10g bhard=11g isoft=10000 ihard=11000 user_group&quot;`&lt;br /&gt;: user_group 그룹에 속한 전체 사용자들의 디스크 용량 및 파일 개수를 제한&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;HTTP 상태코드&lt;/h2&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;코드&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;401&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;인증실패 (Unauthorized)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;403&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;권한 없음 (Forbidden)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;404&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;존재하지 않는 페이지 (Not Found)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;405&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;지정된 방식으로 요청 불가능 (Method Not Allowed)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;502&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;Bad Gateway&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;503&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;Service Unavailable&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;504&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;Gateway Timeout&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;아파치 설정(httpd.conf) 할 때 ErrorDocument 관련하여 설정해야할 수 있음&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;logrotate&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/logrotate.conf&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1761813333088&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;/var/log/wtmp {
	# wtmp 로그파일의 정보를 일반 사용자들이 볼 수 없도록 허가권 및 소유권 지정
	create 0600 root utmp
}&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;h2 data-ke-size=&quot;size26&quot;&gt;파일 관련 명령어&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`chattr` : 파일 속성 변경
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`chattr +a 파일`: 삭제는 불가능, 내용 추가만 가능&lt;/li&gt;
&lt;li&gt;`chattr +i 파일`: 삭제, 변경 불가능&lt;/li&gt;
&lt;li&gt;`lsattr`: 파일 속성 설정된 내용 확인&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;`getfacl`: 파일 접근 통제 리스트 get&lt;/li&gt;
&lt;li&gt;`setfacl`: 파일 접근 통제 리스트 set&lt;/li&gt;
&lt;li&gt;`chmod`: 파일 권한 변경&lt;/li&gt;
&lt;li&gt;`chown`: 파일 소유권 변경&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;make&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`make`: Makefile 을 이용해 바이너리 생성&lt;/li&gt;
&lt;li&gt;`make install`: make 파일로 만들어진 파일을 타깃 디렉터리로 이동&lt;/li&gt;
&lt;li&gt;`make distclean`: 소스코드 압축해제 및 관련정보 초기화, 파일 삭제
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;완전 초기 상태로 바꿔주기 위해 &lt;u&gt;압축파일 등을 삭제&lt;/u&gt;&lt;/li&gt;
&lt;li&gt;제거 명령어 중 가장 강력함&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;`make clean`: 이전에 컴파일한 내용을 삭제&lt;/li&gt;
&lt;li&gt;`make mrproper`: 컴파일에 영향을 주는 정보들 삭제 (이전 컴파일하며 저장된 &lt;u&gt;설정정보 삭제&lt;/u&gt;)&lt;/li&gt;
&lt;li&gt;`make menuconfig`: 텍스트 기반의 메뉴옵션 설정 (&lt;u&gt;커널 컴파일 관련&lt;/u&gt; 옵션 설정임)&lt;/li&gt;
&lt;li&gt;`make xconfig`: X 윈도우 환경의 Qt 기반 설정도구 (옵션설정)&lt;/li&gt;
&lt;li&gt;`make nconfig`: 색상키 지원 (옵션설정)&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;ssh&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;외부 --&amp;gt; 내부: `sshd_config`&lt;/li&gt;
&lt;li&gt;내부 --&amp;gt; 외부: `ssh_config`&lt;/li&gt;
&lt;li&gt;sshd_config 파일에서 `PermitRootLogin no`: root 접근 차단&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;사용자 관련&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;/etc/login.defs
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자에게 부여되는(useradd, groupadd) UID 의 최소/최대값 변경 (번외. mask 설정 가능)&lt;/li&gt;
&lt;li&gt;패스워드 암호화 기법 지정&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/skel
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자 추가 시 기본 제공되는 디렉터리&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;/etc/default/useradd
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;사용자 추가 시 생성되는 홈 디렉터리의 기본 위치를 /users 디렉터리 내에 생성되도록 변경할 수 있음&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;usermod
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`usermod -l kaituser -d /home/kaituser -m ihduser`
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`-l kaituser`: ihduser 사용자명을 kaituser로 변경&lt;/li&gt;
&lt;li&gt;`-d /home/kaituser`: 홈 디렉터리를 /home/ihduser 에서 /home/kaituser 로 변경&lt;/li&gt;
&lt;li&gt;`-m`: 기존에 소유했던 파일이나 디렉터리를 그대로 이용 가능&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;패스워드 변경 관련 명령어: `usermod`, `passwd`, `chage`&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;ipc(inter-process communication, 프로세스 간 통신)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;프로세스는 독립되어 있기 때문에, 내부적으로 통신하기 위해서는 별도의 조치(IPC) 가 필요&lt;/li&gt;
&lt;li&gt;`ipcs -l` : 세마포어 max value 조회 가능&lt;/li&gt;
&lt;li&gt;(+) 연관된지는 모르겠으나, 시험문제에 묶여서 나온 것 같아서..&amp;nbsp;&lt;br /&gt;`/proc/sys/fs/file-max`: 최대 열 수 있는 파일 개수
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;cf) `/proc/sys/fs/file-nr`: 할당된파일 /t 할당되지 않은 파일 /t 최대 오픈 파일&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;외부장치, mount&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;문제 표현 예시: &quot;백업 정보가 담긴 usb 메모리&quot;&lt;/li&gt;
&lt;li&gt;`fdisk`: 디스크 상에서 파티션을 생성/삭제/수정할 수 있는 명령어
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`fdisk -l`: 장착된 디스크 정보 확인 가능 (== `df -h`)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;`/proc/mounts`: 마운트된 장비 정보 조회 가능 (cat으로)&lt;/li&gt;
&lt;li&gt;`/proc/partitions`: 장치의 파티션 정보 확인 가능 (cat)&lt;/li&gt;
&lt;li&gt;`/etc/mtab`: 마운트 되어있는 파일 시스템의 정보 확인 가능&lt;/li&gt;
&lt;li&gt;`mount`: 하드디스크 전체나 특정 파티션을 현재 존재하는 파일시스템의 디렉터리 구조에 붙여 접근 가능하게 만듦&lt;/li&gt;
&lt;li&gt;문제에서 rw 나 /proc/~ 관련해서 나오면 마운트랑 관련되어있을 수 있음&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;rpm&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;자주 쓰는 옵션
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;-gf (find 설치한 패키지명)&lt;/li&gt;
&lt;li&gt;-gfi (info, 패키지 기본정보 출력)&lt;/li&gt;
&lt;li&gt;-gfl (설치한 패키지 목록)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;의존성 관련&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;modinfo&lt;/li&gt;
&lt;li&gt;depmod&lt;/li&gt;
&lt;li&gt;/lib/modules/커널버전/modules.dep&lt;/li&gt;
&lt;/ul&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;h2 data-ke-size=&quot;size26&quot;&gt;커널(kernel)&lt;/h2&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;`uname -r`: 커널 버전정보만 출력&lt;/li&gt;
&lt;/ul&gt;</description>
      <category>Linux</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/30</guid>
      <comments>https://hyewon-s-dev.tistory.com/30#entry30comment</comments>
      <pubDate>Fri, 31 Oct 2025 10:57:24 +0900</pubDate>
    </item>
    <item>
      <title>리눅스마스터 1급 (조금 늦은) 합격 후기, 1차/2차 시험 준비 과정</title>
      <link>https://hyewon-s-dev.tistory.com/29</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;리눅스마스터 1급 1차는 한 번에 합격했는데, 2차는 2번 떨어지면서..ㅎ&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2차 시험만 총 3번의 준비 과정에서 사용했던 자료들이나, 공부 방식 등 시험 준비했던 과정을 기록하고자 늦게라도 작성하고자 한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(23년도에는 공부를 안해서 연기시키고, 본격적인 공부는 24년도부터 했었음)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2025-10-27 오전 11.37.24.png&quot; data-origin-width=&quot;1702&quot; data-origin-height=&quot;792&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bXd3sv/dJMb9V0QlRA/IKePPkIjFDUSah4llsdgWK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bXd3sv/dJMb9V0QlRA/IKePPkIjFDUSah4llsdgWK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bXd3sv/dJMb9V0QlRA/IKePPkIjFDUSah4llsdgWK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbXd3sv%2FdJMb9V0QlRA%2FIKePPkIjFDUSah4llsdgWK%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;1702&quot; height=&quot;792&quot; data-filename=&quot;스크린샷 2025-10-27 오전 11.37.24.png&quot; data-origin-width=&quot;1702&quot; data-origin-height=&quot;792&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;h2 data-ke-size=&quot;size26&quot;&gt;응시 배경&lt;/h2&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;h2 data-ke-size=&quot;size26&quot;&gt;공부했던 메인 교재&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://product.kyobobook.co.kr/detail/S000200689250&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://product.kyobobook.co.kr/detail/S000200689250&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1761533021836&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;website&quot; data-og-title=&quot;2023 이기적 리눅스마스터 1급 기본서 | 김윤수 - 교보문고&quot; data-og-description=&quot;2023 이기적 리눅스마스터 1급 기본서 | 리눅스마스터 1급 2023년 도서가 이기적에서 출간되었습니다. 리눅스마스터 1급을 취득하기 위해 필요한 최대한의 것을 전부 제공해 드립니다. 시행처에서 &quot; data-og-host=&quot;product.kyobobook.co.kr&quot; data-og-source-url=&quot;https://product.kyobobook.co.kr/detail/S000200689250&quot; data-og-url=&quot;https://product.kyobobook.co.kr/detail/S000200689250&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/k3nWy/hyZMotbikc/Mux9Db0mBLqAHgHjMTMRGk/img.jpg?width=458&amp;amp;height=625&amp;amp;face=0_0_458_625,https://scrap.kakaocdn.net/dn/uak8x/hyZMGfdpPp/kLFKPLyqIvzJAKwViIbP10/img.jpg?width=458&amp;amp;height=625&amp;amp;face=0_0_458_625,https://scrap.kakaocdn.net/dn/6IIsw/hyZMj6tLwi/hSh3kWrLDiu0SzKg05G7F1/img.jpg?width=814&amp;amp;height=6529&amp;amp;face=0_0_814_6529&quot;&gt;&lt;a href=&quot;https://product.kyobobook.co.kr/detail/S000200689250&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://product.kyobobook.co.kr/detail/S000200689250&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/k3nWy/hyZMotbikc/Mux9Db0mBLqAHgHjMTMRGk/img.jpg?width=458&amp;amp;height=625&amp;amp;face=0_0_458_625,https://scrap.kakaocdn.net/dn/uak8x/hyZMGfdpPp/kLFKPLyqIvzJAKwViIbP10/img.jpg?width=458&amp;amp;height=625&amp;amp;face=0_0_458_625,https://scrap.kakaocdn.net/dn/6IIsw/hyZMj6tLwi/hSh3kWrLDiu0SzKg05G7F1/img.jpg?width=814&amp;amp;height=6529&amp;amp;face=0_0_814_6529');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;2023 이기적 리눅스마스터 1급 기본서 | 김윤수 - 교보문고&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;2023 이기적 리눅스마스터 1급 기본서 | 리눅스마스터 1급 2023년 도서가 이기적에서 출간되었습니다. 리눅스마스터 1급을 취득하기 위해 필요한 최대한의 것을 전부 제공해 드립니다. 시행처에서&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;product.kyobobook.co.kr&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이기적의 23년도 리눅스마스터 1급 문제집을 활용하였다. 리눅스 환경에는 어느 정도 익숙해져있던 상태였으나,&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;&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;h2 data-ke-size=&quot;size26&quot;&gt;1차 준비&lt;/h2&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://www.comcbt.com/xe/r1&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://www.comcbt.com/xe/r1&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1761533567438&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;website&quot; data-og-title=&quot;리눅스마스터 1급 필기 기출문제 전자문제집 CBT - 최강 자격증 기출문제 전자문제집 CBT&quot; data-og-description=&quot;리눅스마스터 1급 필기 기출문제 전자문제집 CBT&quot; data-og-host=&quot;www.comcbt.com&quot; data-og-source-url=&quot;https://www.comcbt.com/xe/r1&quot; data-og-url=&quot;https://www.comcbt.com/xe/r1&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/i6YFh/hyZMpMnVFZ/s46CYiVyuPBPFHWIX2wTW1/img.jpg?width=290&amp;amp;height=80&amp;amp;face=0_0_290_80&quot;&gt;&lt;a href=&quot;https://www.comcbt.com/xe/r1&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://www.comcbt.com/xe/r1&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/i6YFh/hyZMpMnVFZ/s46CYiVyuPBPFHWIX2wTW1/img.jpg?width=290&amp;amp;height=80&amp;amp;face=0_0_290_80');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;리눅스마스터 1급 필기 기출문제 전자문제집 CBT - 최강 자격증 기출문제 전자문제집 CBT&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;리눅스마스터 1급 필기 기출문제 전자문제집 CBT&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;www.comcbt.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&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;기출만 약 3주 정도, 퇴근한 후 매일 1-2시간씩 문제 반복적으로 풀고 개념 외우고 했던 것 같다.&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;1차 시험 봤을 때, &lt;b&gt;기출에서 나왔던 내용들이 대부분의 문제를 차지&lt;/b&gt;했는데, 동일한 내용으로 문제를 꼬아서 나왔다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;따라서, &lt;b&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;&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;&lt;span style=&quot;color: #ef5369;&quot;&gt;⭐ 1차 시험 시 필수 준비물: 신분증, &lt;b&gt;컴퓨터용 사인펜&lt;/b&gt;, &lt;/span&gt;수험표 출력&lt;span style=&quot;color: #ef5369;&quot;&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;수험표는 필수는 아니지만 수험번호나 신분증 검사 등 여러모로 편했습니다. ((무엇보다 뒤에 답 적어와서 가채점 해볼 수 있음))&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;h2 data-ke-size=&quot;size26&quot;&gt;2차 준비&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2차를 3번이나 봤는데, 떨어진 주 원인 중에 하나는 옵션 몇 개를 계속 빼먹었다..&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이게.. 기출문제에서는 옵션 몇 개를 적어야하는지 확실하게 알려주는데, 실제로 시험문제에서는 옵션 몇 개 적어야하는지 안알려주는 경우가 대부분이라..&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;VM 에 OS 설치해서 man, help 등으로 조회하면서 진짜 많이 보고가야한다.&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;도 필수적으로 풀어보는 것을 추천한다.&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이기적 교재에 나온 기출 중에서는 OS 버전이 높아져, 시험 볼 OS버전으로는 해당되지 않는 경우가 있었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(나의 경우 리눅스 버전 Rocky 8.8 때 시험 봄 - 해당 내용은 &lt;a href=&quot;https://www.ihd.or.kr/introducesubject1.do&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;공식 홈페이지 자격안내&lt;/a&gt; 에서 확인 가능.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;VM에 해당하는 OS 깔고 yum 설치가 되지 않는 명령어 관련 문제는 풀지 않았음)&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;대략 2문제 정도는 진짜 완전 처음보는 유형이 나오긴 하지만, 최신 기출 2-3회차 정도 찾아서 풀면 대부분의 내용이 거기서 나왔던 것 같다.&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;가장 최신 기출들은 찾기 어렵기 때문에, 아래 공식 홈페이지에서 제공하는 &lt;b&gt;답안지를 기반&lt;/b&gt;으로 내용 공부해가는 것을 추천한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://www.ihd.or.kr/guidequestion.do&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://www.ihd.or.kr/guidequestion.do&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1761540570215&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;website&quot; data-og-title=&quot;KAIT 자격검정&quot; data-og-description=&quot;KAIT에서 시행하는 정보통신기술자격검정시험에 많은 관심과 성원을 보내주신 수험자 여러분과 교육 기관관계자 여러분께 감사의 말씀을 드립니다. 급속한 정보통신관련기술 등의 변화로 인해 &quot; data-og-host=&quot;www.ihd.or.kr&quot; data-og-source-url=&quot;https://www.ihd.or.kr/guidequestion.do&quot; data-og-url=&quot;https://www.ihd.or.kr/guidequestion.do&quot; data-og-image=&quot;&quot;&gt;&lt;a href=&quot;https://www.ihd.or.kr/guidequestion.do&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://www.ihd.or.kr/guidequestion.do&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url();&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;KAIT 자격검정&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;KAIT에서 시행하는 정보통신기술자격검정시험에 많은 관심과 성원을 보내주신 수험자 여러분과 교육 기관관계자 여러분께 감사의 말씀을 드립니다. 급속한 정보통신관련기술 등의 변화로 인해&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;www.ihd.or.kr&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&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;기출 풀 때 VM에 OS 설치해서, &lt;b&gt;man, help 등으로 정보를 보고 어떤 내용이 어디에 있는지 대략적으로 파악&lt;/b&gt;해가는 것이 좋다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;오픈북 시험도 공부한 사람만 잘본다고, 첫 2차 시험 때 man, help 믿고 공부 안해갔다가 망했다 ㅎ&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;기출 기반으로 어떤 내용이 나오는지 파악되었다면, man, help 로 어디쯤에 어떤 내용이 있는지 대략적으로 알아가는 것을 추천한다.&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;&lt;b&gt;iptables 관련 문제&lt;/b&gt;는 최신 기출(22년~23년 사이)에서는 다 나왔던 만큼 나올 확률이 90% 넘는데, 옵션이 매우 까다롭다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;iptables 의 table 별 사용하는 옵션들(nat의 PRE/POSTROUTING, 포트번호 등등) 에 들어갈 수 있는 내용들은 외워가서(man 으로 조회 시 일부 옵션 정보는 보이긴 함) 해당 문제푸는 시간을 절약하는 것이 좋다.&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;배점이 높아서 버리고 가기에는 아깝고, 문제 나올 확률도 높기 때문에, iptables 관련 문제는 읽고 바로 풀 수 있을 정도로는 문법 보고가는 것을 추천한다.&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;아래 링크는 2차만 3번 준비하며, 반복적으로 나왔던 내용/정답 작성을 위해 필요한 내용 중심적으로 정리해두었다. 참고는 하되, 가급적이면 직접 기출 풀어보고 자주 나온 것 위주로 정리해보는 것이 좋을 것 같다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/30&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://hyewon-s-dev.tistory.com/30&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1761875887608&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;리눅스마스터 1급 2차 내용 정리&quot; data-og-description=&quot;목차 기출 풀면서 헷갈렸던 부분/자주 나온 유형 위주로 정리해두었습니다.기본적인 내용(파일 위치, 개념 등) 은 포함되지 않아, 개념 공부 후 보시면 좋을 것 같습니다. (혹시 틀린 정보 있다면&quot; data-og-host=&quot;hyewon-s-dev.tistory.com&quot; data-og-source-url=&quot;https://hyewon-s-dev.tistory.com/30&quot; data-og-url=&quot;https://hyewon-s-dev.tistory.com/30&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/Rt7I3/hyZLnaPkJu/neEf1pKbzgxz0XEaBmcWa0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/fbDMZ/hyZMKoWUzL/gYA1GdH2HFO9qbpdqIi5Y1/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bkUJLs/hyZMR2D79X/4xu4YdKbwkv3QEQnuXiT51/img.jpg?width=1170&amp;amp;height=878&amp;amp;face=0_0_1170_878&quot;&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/30&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://hyewon-s-dev.tistory.com/30&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/Rt7I3/hyZLnaPkJu/neEf1pKbzgxz0XEaBmcWa0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/fbDMZ/hyZMKoWUzL/gYA1GdH2HFO9qbpdqIi5Y1/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bkUJLs/hyZMR2D79X/4xu4YdKbwkv3QEQnuXiT51/img.jpg?width=1170&amp;amp;height=878&amp;amp;face=0_0_1170_878');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;리눅스마스터 1급 2차 내용 정리&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;목차 기출 풀면서 헷갈렸던 부분/자주 나온 유형 위주로 정리해두었습니다.기본적인 내용(파일 위치, 개념 등) 은 포함되지 않아, 개념 공부 후 보시면 좋을 것 같습니다. (혹시 틀린 정보 있다면&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;hyewon-s-dev.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #ef5369;&quot;&gt;⭐ 2차 시험 시 필수 준비물: 신분증,&lt;span&gt;&amp;nbsp;검정볼펜&lt;/span&gt;, 화이트&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;수험표 출력&lt;span style=&quot;color: #ef5369;&quot;&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;화이트는 매 시험마다 사용 가능여부가 달랐던 것 같다. 사용 가능하면 편하니 챙겨가는 것을 추천한다.&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;일찍가서 yum으로 설치 안된 패키지 설치하고, conf 파일들 검토해보는 것&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;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 시험장 가서 yum 패키지 설치 확인을 위해 기록해놨던 내용이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;OS 버전마다 다르기도하고 무엇보다 나도 공부하면서 작성해둔 것이기 때문에, 정확하지 않을 수 있어 참고용으로만 확인하길 바람.&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%; height: 274px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot; data-ke-style=&quot;style8&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;프로그램명&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;데몬 이름&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;참고&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;bind&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;named&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;DNS 관련&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;sendmail&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;squid&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;프록시&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;net-tools&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;이더넷 확인. ifconfig, netstat&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;rsync&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;데이터 백업&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;httpd&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;아파치(apache)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;quota&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;quota, edquota&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;cups-lpd&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;lp, lpr&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;프린트&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;samba&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;samba-client&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;make&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 19px; text-align: center;&quot;&gt;vsftpd&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 19px; text-align: center;&quot;&gt;vsftpd&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 19px; text-align: center;&quot;&gt;FTP (파일전송)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;nfs-utils&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;exportfs, showmount&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;nfs (파일 mount 관련)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;nmap&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;사용 중인 포트조회 가능&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 29.4186%; height: 17px; text-align: center;&quot;&gt;dhcp.server&lt;/td&gt;
&lt;td style=&quot;width: 33.9535%; height: 17px; text-align: center;&quot;&gt;dhcpd&lt;/td&gt;
&lt;td style=&quot;width: 36.6279%; height: 17px; text-align: center;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&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;h2 data-ke-size=&quot;size26&quot;&gt;후기&lt;/h2&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;시험 준비하면서 서버의 인프라 구조체에 대해서 정말 많이 공부되었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;nfs, nis, dns 등 학부 때 개념으로만 알고있던 내용들을, 실제로 어떻게 설정하여 사용되고 있는지에 대한 전반적인 부분에 대해 이해할 수 있는 시간이었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;업계에서 해당 자격증을 어떻게 바라보고있는지는 잘 모르겠지만, 개인적으로 자격증 준비하면서 새로 알게된 기술지식이 많아, IT 업계에 종사하는 주니어라면 자격증 준비하는 것을 추천한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>자격증</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/29</guid>
      <comments>https://hyewon-s-dev.tistory.com/29#entry29comment</comments>
      <pubDate>Mon, 27 Oct 2025 15:09:48 +0900</pubDate>
    </item>
    <item>
      <title>vim 문자열 일괄 변경/규칙적인 문자열도 일괄 변경가능(feat.정규표현식)</title>
      <link>https://hyewon-s-dev.tistory.com/28</link>
      <description>&lt;h3 data-ke-size=&quot;size23&quot;&gt;문자열 일괄 변경 명령어&lt;/h3&gt;
&lt;pre id=&quot;code_1718330500185&quot; class=&quot;shell&quot; data-ke-language=&quot;shell&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;:%s/{변경 전 단어}/{변경 후 단어}/g&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. 파일 내에 있는 test라는 단어를 up 으로 변경하고 싶을 경우&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1718330624516&quot; class=&quot;shell&quot; data-ke-language=&quot;shell&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;:%s/test/up/g&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;h3 data-ke-size=&quot;size23&quot;&gt;규칙적인 문자열 변경(정규표현식 이용)&lt;/h3&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;ex. test1.not, test2.not, test3.not ... 과 같은 문자들을 일괄적으로 지우고 싶을 경우, 위 기본 명령어에 {변경 전 단어} 파트에 정규표현식 이용해서 작성&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1718330843405&quot; class=&quot;shell&quot; data-ke-language=&quot;shell&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;:%s/test\+[0-9]\+.not//g&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>Linux</category>
      <category>Linux</category>
      <category>vi</category>
      <category>vim</category>
      <category>일괄변경</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/28</guid>
      <comments>https://hyewon-s-dev.tistory.com/28#entry28comment</comments>
      <pubDate>Fri, 14 Jun 2024 11:10:49 +0900</pubDate>
    </item>
    <item>
      <title>[Linux/Python] python Linux vi 로 작성했을 때 indentation 에러</title>
      <link>https://hyewon-s-dev.tistory.com/27</link>
      <description>&lt;h3 data-ke-size=&quot;size23&quot;&gt;[발생한 에러]&lt;/h3&gt;
&lt;pre id=&quot;code_1716346078544&quot; class=&quot;actionscript&quot; data-ke-type=&quot;codeblock&quot; data-ke-language=&quot;bash&quot;&gt;&lt;code&gt;TabError: inconsistent use of tabs and spaces in indentation&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;os 버전: rhel8&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;centos7 에서 수정했을 땐 발생하지 않던 에러 발생..&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위 코드와 tab 정렬도 잘 맞췄는데 자꾸 발생하길래, vi 내에서 /^I 로 검색해보니, 작성한 라인만 tab이 아닌 띄어쓰기로 작성됨.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;[해결]&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. 내 디렉터리에 .vimrc 파일 만들어 set expandtab 작성 - tab을 띄어쓰기로 만들어줌.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 작성한 코드 vi로 들어가 :retab 실행&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;tab으로 작성된 모든 코드들이 전부 띄어쓰기로 변경됨&lt;/p&gt;</description>
      <category>Cloud/ERROR</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/27</guid>
      <comments>https://hyewon-s-dev.tistory.com/27#entry27comment</comments>
      <pubDate>Wed, 22 May 2024 11:53:59 +0900</pubDate>
    </item>
    <item>
      <title>chmod 특수권한(set-uid, set-gid, sticky-bit)</title>
      <link>https://hyewon-s-dev.tistory.com/26</link>
      <description>&lt;h3 data-ke-size=&quot;size23&quot;&gt;set-uid(4)&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;-  설정: u+s&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 제거: u-s&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;h3 data-ke-size=&quot;size23&quot;&gt;set-gid(2)&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 설정: g+s&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 제거: g-s&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 그룹 소유자 접근 권한의 실행 권한 자리에 실행 권한이 있으면 소문자 s로, 실행 권한이 없으면 대문자 S로 표시됨&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h3 data-ke-size=&quot;size23&quot;&gt;sticky-bit(1)&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 설정: o+t&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 제거: o-t&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;- 특정 디렉토리를 누구나 자유롭게 이용 가능. 그러나 소유자 or 슈퍼유저가 아니면 삭제, 변경 못함. 생성은 가능&lt;/p&gt;</description>
      <category>Linux</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/26</guid>
      <comments>https://hyewon-s-dev.tistory.com/26#entry26comment</comments>
      <pubDate>Thu, 9 May 2024 14:40:08 +0900</pubDate>
    </item>
    <item>
      <title>numpy array 전체, 일렬로 출력</title>
      <link>https://hyewon-s-dev.tistory.com/25</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;일반적으로 numpy array 출력 시 아래와 같이 출력&lt;/p&gt;
&lt;pre id=&quot;code_1710384243040&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[[-1 -1 -1 ... -1 -1 -1]
 [-1 -1 -1 ... -1 -1 -1]
 [-1 -1  1 ... -1 -1 -1]
 ...
 [-1 -1 -1 ... -1 -1 -1]
 [-1 -1 -1 ... -1 -1 -1]
 [-1 -1 -1 ... -1 -1 -1]]&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;아래 옵션 주면 전체 출력됨&lt;/p&gt;
&lt;pre id=&quot;code_1710384279807&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;import sys
import numpy as np
np.set_printoptions(threshold=sys.maxsize)&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre id=&quot;code_1710384327104&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[[-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1  1 -1  0 -1  0 -1  0 -1  0 -1  0 -1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1  1 -1  0 -1  1 -1 -1 -1  1 -1 -1 -1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1  1 -1  0 -1  1 -1  1 -1  0 -1  1 -1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]
 [-1 -1  1 -1  1 -1  1 -1 -1 -1  0 -1  1 -1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
  -1 -1 -1]]&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;일렬로 출력하려면 linewidth inf 옵션 추가&lt;/p&gt;
&lt;pre id=&quot;code_1710384388980&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[[-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  1  1  1  1  1  1  1  1  1  1  1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1  1  1  1  1  1  0  0  0  0  0  1  1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1  1  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1  1  1  1  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1  1  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1  1  1  1  1  1  0  0  0  1  1  1  1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1  1  0  0  0  0  0  0  0  0  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1  1  1  1  1  1  0  0  0  1  1  1  1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1  1  0  0  0  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1  1  1  1  1  1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]
 [-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1]]&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 data-ke-size=&quot;size16&quot;&gt;전체 옵션 코드&lt;/p&gt;
&lt;pre id=&quot;code_1710384452375&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;import sys
import numpy as np
np.set_printoptions(threshold=sys.maxsize, linewidth=np.inf)&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>Programming Language/Python</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/25</guid>
      <comments>https://hyewon-s-dev.tistory.com/25#entry25comment</comments>
      <pubDate>Thu, 14 Mar 2024 11:48:29 +0900</pubDate>
    </item>
    <item>
      <title>Access, Modify, Change Time 정리</title>
      <link>https://hyewon-s-dev.tistory.com/24</link>
      <description>&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Access Time(접근 시간): 파일을 읽은 마지막 시간&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Modify Time(수정 시간): 파일의 내용이 변경되었던 마지막 시간&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Change Time(변경 시간): 파일의 허가권과 같은 상태가 변경되었던 시간.&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&amp;nbsp;touch
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;1. 파일의 크기가 0인 빈 파일을 만들 때 사용&lt;/span&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;/span&gt;&lt;/li&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;2. 파일의 Access Time, &lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Modify Time&lt;/span&gt; 변경 가능&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000;&quot;&gt;stat&lt;/span&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;span style=&quot;color: #000000;&quot;&gt;Access Time, Modify Time, Change Time 조회 가능&lt;/span&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&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 style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;헷갈리지 말아야할 부분이, touch는 Change Time을 변경하는 것은 아님.&lt;/span&gt;&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;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Access Time과 Modify Time은 touch를 활용하여 원하는 시점으로 기록할 수 있지만,&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;&lt;span style=&quot;color: #000000; text-align: start;&quot;&gt;Change Time 은 Access Time과 Modify Time이 변경되는 시점이 기록되는 것이기 때문에, 변경이 되긴 하지만, 위 두 개와는 계열이 다름&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;</description>
      <category>Linux</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/24</guid>
      <comments>https://hyewon-s-dev.tistory.com/24#entry24comment</comments>
      <pubDate>Sat, 9 Mar 2024 11:33:04 +0900</pubDate>
    </item>
    <item>
      <title>[Web/Map] Kakao 지도 Python API 공공데이터 활용해 Javascript로 Polyline 그리기</title>
      <link>https://hyewon-s-dev.tistory.com/22</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;포스터는 다음과 같이 진행될 예정.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;[Kakao 지도 API를 이용한 길찾기 웹 만들기]&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(2) &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Kakao 지도 &lt;/span&gt;Javascript를 이용해 Marker 이용해보기&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;(3) &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Kakao 지도 &lt;/span&gt;Javascript를 이용해 InfoWindow 이용해보기&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333; text-align: start;&quot;&gt;(4) &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Kakao 지도&lt;/span&gt; Python API 공공데이터 활용해 &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Javascript로&lt;/span&gt; Polyline 그리기&lt;span&gt;&amp;nbsp;&lt;span style=&quot;background-color: #f6e199; color: #666666; text-align: start;&quot;&gt; 현재 포스터 &lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(5) 길찾기 API ODsay, Python을 이용한 실시간 길찾기 데이터 불러오기&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(6) 백엔드로 불러온 실시간 길찾기 데이터 지도에 polyline 찍어보기&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;동기들과 구현해본 길찾기 서비스에 대한 기록.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;학부생 수준으로 진행한 것이라 메모리 사용량이든 디스크 사용량이든 정말 비효율적으로 만들어지긴 했는데,&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;지도를 입문하거나, 길찾기를 지도에 적용하고 싶은데 너무 막연하게 느껴진다면 도움은 될 것 같다.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;[포스터 참고]&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용:&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/16&quot;&gt;https://hyewon-s-dev.tistory.com/16&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1693182635787&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;[Web/Map] Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용/위도경도 찾는 법&quot; data-og-description=&quot;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용  현재 포스터  (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWi&quot; data-og-host=&quot;hyewon-s-dev.tistory.com&quot; data-og-source-url=&quot;https://hyewon-s-dev.tistory.com/16&quot; data-og-url=&quot;https://hyewon-s-dev.tistory.com/16&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/brUqWV/hyTICdYUBd/9cB5bGCrNNQXZwk7chDAwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bzL46q/hyTIQJ2h0L/jSrGczOBj5X4BiNqXK72KK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bkSYiV/hyTL98251r/Z3aeIZvyNP23F6bHKnhPKk/img.png?width=3008&amp;amp;height=1496&amp;amp;face=0_0_3008_1496&quot;&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/16&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://hyewon-s-dev.tistory.com/16&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/brUqWV/hyTICdYUBd/9cB5bGCrNNQXZwk7chDAwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bzL46q/hyTIQJ2h0L/jSrGczOBj5X4BiNqXK72KK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/bkSYiV/hyTL98251r/Z3aeIZvyNP23F6bHKnhPKk/img.png?width=3008&amp;amp;height=1496&amp;amp;face=0_0_3008_1496');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;[Web/Map] Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용/위도경도 찾는 법&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용  현재 포스터  (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWi&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;hyewon-s-dev.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&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 style=&quot;background-color: #ffffff; color: #666666; text-align: start;&quot;&gt;(2)&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - Marker&lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #666666; text-align: start;&quot;&gt;&amp;nbsp;:&lt;/span&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/17&quot;&gt;https://hyewon-s-dev.tistory.com/17&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1693182643874&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;[Web/Map] Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기(1) - Marker&quot; data-og-description=&quot;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용 (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - Ma&quot; data-og-host=&quot;hyewon-s-dev.tistory.com&quot; data-og-source-url=&quot;https://hyewon-s-dev.tistory.com/17&quot; data-og-url=&quot;https://hyewon-s-dev.tistory.com/17&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/1JyIp/hyTMfg67Bo/H0Q24dbOY4OR2xBHF8YPB0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/quBGv/hyTIJ5dMiJ/caNq24UQiPL1UjgPIE9MwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/cxpA2k/hyTMdcxe0B/hPoocOi1RiJK9WBttK50T1/img.png?width=1332&amp;amp;height=986&amp;amp;face=0_0_1332_986&quot;&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/17&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://hyewon-s-dev.tistory.com/17&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/1JyIp/hyTMfg67Bo/H0Q24dbOY4OR2xBHF8YPB0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/quBGv/hyTIJ5dMiJ/caNq24UQiPL1UjgPIE9MwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/cxpA2k/hyTMdcxe0B/hPoocOi1RiJK9WBttK50T1/img.png?width=1332&amp;amp;height=986&amp;amp;face=0_0_1332_986');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;[Web/Map] Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기(1) - Marker&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용 (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - Ma&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;hyewon-s-dev.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(3) &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - &lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;InfoWindow&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #666666; text-align: start;&quot;&gt;&amp;nbsp;:&lt;/span&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/17&quot;&gt;https://hyewon-s-dev.tistory.com/17&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1693182672852&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;[Web/Map] Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기(1) - Marker&quot; data-og-description=&quot;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용 (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - Ma&quot; data-og-host=&quot;hyewon-s-dev.tistory.com&quot; data-og-source-url=&quot;https://hyewon-s-dev.tistory.com/17&quot; data-og-url=&quot;https://hyewon-s-dev.tistory.com/17&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/1JyIp/hyTMfg67Bo/H0Q24dbOY4OR2xBHF8YPB0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/quBGv/hyTIJ5dMiJ/caNq24UQiPL1UjgPIE9MwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/cxpA2k/hyTMdcxe0B/hPoocOi1RiJK9WBttK50T1/img.png?width=1332&amp;amp;height=986&amp;amp;face=0_0_1332_986&quot;&gt;&lt;a href=&quot;https://hyewon-s-dev.tistory.com/17&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://hyewon-s-dev.tistory.com/17&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/1JyIp/hyTMfg67Bo/H0Q24dbOY4OR2xBHF8YPB0/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/quBGv/hyTIJ5dMiJ/caNq24UQiPL1UjgPIE9MwK/img.png?width=800&amp;amp;height=800&amp;amp;face=0_0_800_800,https://scrap.kakaocdn.net/dn/cxpA2k/hyTMdcxe0B/hPoocOi1RiJK9WBttK50T1/img.png?width=1332&amp;amp;height=986&amp;amp;face=0_0_1332_986');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;[Web/Map] Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기(1) - Marker&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;포스터는 다음과 같이 진행될 예정. [Kakao 지도 API를 이용한 길찾기 웹 만들기] (1) Kakao 지도 API 키 발급 및 HTML5 + Javascript 적용 (2) Javascript를 이용한 Kakao 지도 Marker, Polyline, InfoWindow 이용해보기 - Ma&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;hyewon-s-dev.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&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 style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;+ 이상한 부분이나 틀린 부분, 피드백 대환영입니다.&lt;/span&gt;&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 style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: center;&quot; data-ke-size=&quot;size16&quot;&gt;출발지와 도착지의 위치를 찍어주는 핀 &amp;rarr; 마커&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: center;&quot; data-ke-size=&quot;size16&quot;&gt;지도 위에서 출발지에서 도착지까지 가는 경로를 그려준 색깔 선 &amp;rarr; 폴리라인&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: center;&quot; data-ke-size=&quot;size16&quot;&gt;출발지와 도착지 등 특정 장소에 대해 설명해주는 말풍선 창 &amp;rarr; 인포윈도우&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;로, 이것들을 이용하고, 응용 해보고자 함&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(1)번 포스터에서 언급한 vscod&lt;span style=&quot;color: #333333;&quot;&gt;e 에디터,&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;HTML Live Server 확장자를 설치하면 실습에 따라오기 더 편할 것 같다.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;&lt;b&gt;[코드 기본 셋팅]&lt;/b&gt; main.html&lt;span style=&quot;background-color: #ffffff; color: #000000; text-align: left;&quot;&gt; &lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #000000; text-align: left;&quot;&gt; &lt;/span&gt;&lt;span style=&quot;background-color: #ffffff; color: #000000; text-align: left;&quot;&gt; &lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;pre id=&quot;code_1693183365119&quot; class=&quot;html xml&quot; data-ke-language=&quot;html&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;&amp;lt;!DOCTYPE html&amp;gt;
&amp;lt;html&amp;gt;
&amp;lt;head&amp;gt;
    &amp;lt;title&amp;gt;카카오 지도&amp;lt;/title&amp;gt;
    &amp;lt;script type=&quot;text/javascript&quot; src=&quot;//dapi.kakao.com/v2/maps/sdk.js?appkey={{javascript 키}}&amp;amp;libraries=services,clusterer,drawing&quot;&amp;gt;&amp;lt;/script&amp;gt;
&amp;lt;/head&amp;gt;
&amp;lt;body&amp;gt;
    &amp;lt;div id=&quot;map&quot; style=&quot;width:500px;height:400px;&quot;&amp;gt;&amp;lt;/div&amp;gt;
    &amp;lt;script&amp;gt;
		var container = document.getElementById('map');
		var options = {
			center: new kakao.maps.LatLng(33.450701, 126.570667),
			level: 5
            
		};

		var map = new kakao.maps.Map(container, options);
	&amp;lt;/script&amp;gt;
&amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h3 style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size23&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;1. 지도에 선긋기&lt;/span&gt;&lt;/span&gt;&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;일단 가장 기본적인 선 긋는 방법부터 실습.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;선은 `kakao.maps.Polyline` 모듈 이용. linePath로 선을 그을 좌표를 list 형태를 지정해준 후,&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;선의 색깔, 스타일, 투명도 등과 같은 옵션 사용해서 그리게 된다. &lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;공식 홈페이지에 있는 예시 코드이며, 위 기본 코드 중 map 변수 아래에 js 언어로 작성해주면 됨.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;pre id=&quot;code_1693184686558&quot; class=&quot;javascript&quot; data-ke-language=&quot;javascript&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;// 선을 구성하는 좌표 배열입니다. 이 좌표들을 이어서 선을 표시합니다
var linePath = [
    new kakao.maps.LatLng(33.452344169439975, 126.56878163224233),
    new kakao.maps.LatLng(33.452739313807456, 126.5709308145358),
    new kakao.maps.LatLng(33.45178067090639, 126.5726886938753) 
];

var polyline = new kakao.maps.Polyline({
    path: linePath, // 선을 구성하는 좌표배열 입니다
    strokeWeight: 5, // 선의 두께 입니다
    strokeColor: '#FFAE00', // 선의 색깔입니다
    strokeOpacity: 0.7, // 선의 불투명도 입니다 1에서 0 사이의 값이며 0에 가까울수록 투명합니다
    strokeStyle: 'solid' // 선의 스타일입니다
});

// 지도에 선을 표시합니다 
polyline.setMap(map);&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2023-08-28 오전 10.09.35.png&quot; data-origin-width=&quot;1122&quot; data-origin-height=&quot;984&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dF19A0/btssqlIKm3A/e4g6FYdPUsvCYx165hGPr0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dF19A0/btssqlIKm3A/e4g6FYdPUsvCYx165hGPr0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dF19A0/btssqlIKm3A/e4g6FYdPUsvCYx165hGPr0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdF19A0%2FbtssqlIKm3A%2Fe4g6FYdPUsvCYx165hGPr0%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;565&quot; height=&quot;496&quot; data-filename=&quot;스크린샷 2023-08-28 오전 10.09.35.png&quot; data-origin-width=&quot;1122&quot; data-origin-height=&quot;984&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;일반적으로, 위와 같은 선이 그어져있는 곳을 생각한다면,&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;로드뷰를 보고싶을 때, 클릭 가능한 위치를 띄울 때에도 지도 속에 라인이 그려져있고,&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;길찾기를 했을 때, 출발 지점부터 도착 지점까지 선이 그어져있는 것을 확인할 수 있다.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위와 같은 방법으로 선을 찍으려고 한다면, 선의 모서리 부분에 대한 좌표의 데이터를 가지고 있으면 된다. (아래 사진 참고)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2023-08-28 오전 10.09.35.png&quot; data-origin-width=&quot;1122&quot; data-origin-height=&quot;984&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bDXSp4/btssf1E3lVi/96gknInwezNafXdk47X87K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bDXSp4/btssf1E3lVi/96gknInwezNafXdk47X87K/img.png&quot; data-alt=&quot;동그라미 친 부분에 대한 좌표 데이터가 필요&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bDXSp4/btssf1E3lVi/96gknInwezNafXdk47X87K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbDXSp4%2Fbtssf1E3lVi%2F96gknInwezNafXdk47X87K%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;547&quot; height=&quot;480&quot; data-filename=&quot;스크린샷 2023-08-28 오전 10.09.35.png&quot; data-origin-width=&quot;1122&quot; data-origin-height=&quot;984&quot;/&gt;&lt;/span&gt;&lt;figcaption&gt;동그라미 친 부분에 대한 좌표 데이터가 필요&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;만약 선이 직선이 아니라면, 위와 같이 좌표를 쪼개서 선을 그려주면 되는 것임.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h3 style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size23&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;2. 공공데이터를 활용해 지도에 Polyline 그려보기&lt;/span&gt;&lt;/span&gt;&lt;/h3&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;Python을 이용하여 API로 데이터를 불러와, Python 웹 프레임워크 Flask 를 이용하여 데이터를 프론트로 이동시키고,&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;이동된 데이터를 활용해 지도에 Polyline을 찍는 흐름으로 진행. 주제에 벗어나지 않는 선으로 작성.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;[사용할 데이터] 서울특별시_서울시 자치구별 도보 네트워크 공간정보&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;&lt;a href=&quot;http://data.seoul.go.kr/dataList/OA-21208/S/1/datasetView.do&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;http://data.seoul.go.kr/dataList/OA-21208/S/1/datasetView.do&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1697092918693&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;website&quot; data-og-title=&quot;서울시 자치구별 도보 네트워크 공간정보&quot; data-og-description=&quot;서울시내 보행자도로를 노드 링크 기반으로 표현한 위치정보 서비스입니다. &amp;lt;br /&amp;gt;대로변의 횡단보도와 육교, 버스정류장, 지하철 출입구 등의 정보를 확인할 수 있습니다. ('20년 기준) &amp;lt;br /&amp;gt;좌표&quot; data-og-host=&quot;data.seoul.go.kr&quot; data-og-source-url=&quot;http://data.seoul.go.kr/dataList/OA-21208/S/1/datasetView.do&quot; data-og-url=&quot;https://data.seoul.go.kr&quot; data-og-image=&quot;&quot;&gt;&lt;a href=&quot;http://data.seoul.go.kr/dataList/OA-21208/S/1/datasetView.do&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;http://data.seoul.go.kr/dataList/OA-21208/S/1/datasetView.do&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url();&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;서울시 자치구별 도보 네트워크 공간정보&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;서울시내 보행자도로를 노드 링크 기반으로 표현한 위치정보 서비스입니다. &amp;lt;br /&amp;gt;대로변의 횡단보도와 육교, 버스정류장, 지하철 출입구 등의 정보를 확인할 수 있습니다. ('20년 기준) &amp;lt;br /&amp;gt;좌표&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;data.seoul.go.kr&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;먼저 간단하게 필요한 데이터를 분석해보면,&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2023-08-28 오전 11.11.25.png&quot; data-origin-width=&quot;1984&quot; data-origin-height=&quot;1258&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bdKXds/btssc9RdZEG/l8xF213OowNiEeqH8NrjG0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bdKXds/btssc9RdZEG/l8xF213OowNiEeqH8NrjG0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bdKXds/btssc9RdZEG/l8xF213OowNiEeqH8NrjG0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbdKXds%2Fbtssc9RdZEG%2Fl8xF213OowNiEeqH8NrjG0%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;1984&quot; height=&quot;1258&quot; data-filename=&quot;스크린샷 2023-08-28 오전 11.11.25.png&quot; data-origin-width=&quot;1984&quot; data-origin-height=&quot;1258&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%; height: 87px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot; data-ke-style=&quot;style8&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 19px;&quot;&gt;
&lt;td style=&quot;width: 15.5814%; height: 19px; text-align: center;&quot;&gt;Column 이름&lt;/td&gt;
&lt;td style=&quot;width: 12.6744%; height: 19px; text-align: center;&quot;&gt;Value 값 종류&lt;/td&gt;
&lt;td style=&quot;width: 71.7442%; height: 19px; text-align: center;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 15.5814%; height: 34px; text-align: center;&quot; rowspan=&quot;2&quot;&gt;노드 링크 유형&lt;/td&gt;
&lt;td style=&quot;width: 12.6744%; height: 17px; text-align: center;&quot;&gt;LINK&lt;/td&gt;
&lt;td style=&quot;width: 71.7442%; height: 17px;&quot;&gt;선으로 연결된 데이터&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 12.6744%; height: 17px; text-align: center;&quot;&gt;NODE&lt;/td&gt;
&lt;td style=&quot;width: 71.7442%; height: 17px;&quot;&gt;지점 하나&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 15.5814%; height: 17px; text-align: center;&quot;&gt;노드 WKT&lt;/td&gt;
&lt;td style=&quot;width: 12.6744%; height: 17px; text-align: center;&quot;&gt;-&lt;/td&gt;
&lt;td style=&quot;width: 71.7442%; height: 17px;&quot;&gt;노드 링크 유형이 NODE일 경우, 특정 지점(POINT)의 위도, 경도&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 15.5814%; height: 17px; text-align: center;&quot;&gt;링크 WKT&lt;/td&gt;
&lt;td style=&quot;width: 12.6744%; height: 17px; text-align: center;&quot;&gt;-&lt;/td&gt;
&lt;td style=&quot;width: 71.7442%; height: 17px;&quot;&gt;노드 링크 유형이 LINK일 경우, 도보로 다닐 수 있는 거리에 대한 선의 위도/경도&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이렇게 4가지가 될 것 같다. 데이터를 Python을 이용해 불러오는 코드는 파일 생성해서 아래 코드 작성.&lt;/p&gt;
&lt;pre id=&quot;code_1693189202596&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# modules.py
def api_json(url):
    import ssl, json
    from urllib.request import Request, urlopen
    request = Request(url)
    context = ssl._create_unverified_context()
    response = urlopen(request, context=context) # 데이터 불러오기
    response_body = response.read().decode('utf-8')
    return json.loads(response_body)

class network_geo_info:
    def __init__(self, city_country):
        self.s_key = '{플랫폼에서 받은 secret key}'
        self.city_country = city_country
        self.link_list = []
        self.node_list = []
    
    def list_total_count(self):
        from urllib.parse import quote
        query = quote(self.city_country)
        url = f'http://openapi.seoul.go.kr:8088/{self.s_key}/json/TbTraficWlkNet/0/1/' + query
        data_json = api_json(url)
        total_idx = int(data_json['TbTraficWlkNet']['list_total_count'])
        return total_idx

    def read_data_json(self, strt_pg, end_pg):
        from urllib.parse import quote
        query = quote(self.city_country)
        url = f'http://openapi.seoul.go.kr:8088/{self.s_key}/json/TbTraficWlkNet/{strt_pg}/{end_pg}/' + query
        data_json = api_json(url)
        return data_json

    def make_link_list(self, data_json):
        for idx in range(len(data_json['TbTraficWlkNet']['row'])):
            if data_json['TbTraficWlkNet']['row'][idx]['TYPE'] == 'LINK':
                link_list4append = []
                position_str = data_json['TbTraficWlkNet']['row'][idx]['LINK_WKT'].lstrip('LINESTRING').strip('('')')
                _position_list = position_str.split(',')
                for position in _position_list:
                    link_list4append.append(position.split(' '))
                self.link_list.append(link_list4append)
            elif data_json['TbTraficWlkNet']['row'][idx]['TYPE'] == 'NODE':
                node_position = data_json['TbTraficWlkNet']['row'][idx]['NODE_WKT'].lstrip('POINT').strip('('')').split(' ')
                self.node_list.append(node_position)&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;간단한 실행은 위 함수 작성한 아래에 아래 코드 넣어서 실행해보면 됨&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;pre id=&quot;code_1693189392336&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;NW_info = network_geo_info(&quot;노원구&quot;) # 시군구명 적어넣으면 됨. 여기선 예시로 노원구
data_json = NW_info.read_data_json(0, 999) # 시작 index와 끝 index 작성
NW_info.make_link_list(data_json) # link, node 데이터 각각 따로 저장

# print로 확인해보기
NW_link_list = NW_info.link_list
NW_node_list = NW_info.node_list
print(NW_link_list)
print(NW_node_list)&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;[기본 셋팅]&lt;/span&gt;&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot;&gt;참고 - Flask는 폴더 생성 경로, 폴더명이 매우 중요. 아래 사진 참고(빨간건 무시해주세요.)&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2023-10-12 오후 5.37.57.png&quot; data-origin-width=&quot;302&quot; data-origin-height=&quot;268&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bijOi2/btsydnBRJ9L/ikN7A0prJekXTwZPsyVw20/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bijOi2/btsydnBRJ9L/ikN7A0prJekXTwZPsyVw20/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bijOi2/btsydnBRJ9L/ikN7A0prJekXTwZPsyVw20/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbijOi2%2FbtsydnBRJ9L%2FikN7A0prJekXTwZPsyVw20%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;252&quot; height=&quot;224&quot; data-filename=&quot;스크린샷 2023-10-12 오후 5.37.57.png&quot; data-origin-width=&quot;302&quot; data-origin-height=&quot;268&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #333333;&quot;&gt;&lt;span style=&quot;background-color: #ffffff; text-align: start;&quot;&gt;1. 프로젝트 폴더 하나 만들어준 다음(여기서는 myprj로 만듦), 그 안에 &lt;a href=&quot;https://hyewon-s-dev.tistory.com/14&quot;&gt;가상환경 설치(링크 참고)&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;2. main.py 파일 생성&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;3. modules.py 파일 생성 후 위 코드 복붙&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;4. 폴더명 templates 으로 폴더 생성&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;5. templates 폴더 안에 main.html 파일 생성&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;파이썬 코드는 간단하게 넘어가겠습니다.&lt;/p&gt;
&lt;pre id=&quot;code_1697100142956&quot; class=&quot;python&quot; data-ke-language=&quot;python&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;# main.py --&amp;gt; flask가 실행되는 가장 메인이 되는 파이썬 파일
from flask import Flask, render_template, jsonify

from modules import api_json, network_geo_info

app = Flask(__name__)
app.config['JSON_AS_ASCII'] = False

@app.route('/')
def main():
    NW_info = network_geo_info(&quot;노원구&quot;)
    NW_total_count = NW_info.list_total_count()
    for idx in range(0, NW_total_count, 1000):
        data_json = NW_info.read_data_json(idx, idx+999)
        NW_info.make_link_list(data_json)
    # print(NW_info.link_list[0]) # [['127.08374812215546', '37.64624447253883'], ['127.08403711977205', '37.646315129324364']]
    # print(NW_info.node_list[0]) # ['127.06406830919677', '37.658457824591615']
    return render_template('main.html', NW_link_list=NW_info.link_list)

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000, debug=True)&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;프론트를 구성하는 main.html 전체 코드&lt;/p&gt;
&lt;pre id=&quot;code_1697100226166&quot; class=&quot;html xml&quot; data-ke-language=&quot;html&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;&amp;lt;!DOCTYPE html&amp;gt;
&amp;lt;html&amp;gt;
&amp;lt;head&amp;gt;
    &amp;lt;title&amp;gt;카카오 지도&amp;lt;/title&amp;gt;
    &amp;lt;script type=&quot;text/javascript&quot; src=&quot;//dapi.kakao.com/v2/maps/sdk.js?appkey={{javascript 키}}&amp;amp;libraries=services,clusterer,drawing&quot;&amp;gt;&amp;lt;/script&amp;gt;
	&amp;lt;script&amp;gt;
        var NW_link_list = {{ NW_link_list|tojson }};
    &amp;lt;/script&amp;gt;
&amp;lt;/head&amp;gt;
&amp;lt;body&amp;gt;
    &amp;lt;div id=&quot;map&quot; style=&quot;width:1000px;height:1000px;&quot;&amp;gt;&amp;lt;/div&amp;gt;
    &amp;lt;script&amp;gt;
		var container = document.getElementById('map');
		var options = {
			center: new kakao.maps.LatLng(37.6574151, 127.0678763),
			level: 4
            
		};

		var map = new kakao.maps.Map(container, options);

		for (var i = 0; i &amp;lt; NW_link_list.length; i++) {
			var linePath = []; // 선을 구성하는 좌표 배열입니다. 이 좌표들을 이어서 선을 표시합니다
			for (var j = 0; j &amp;lt; NW_link_list[i].length; j++) {
				linePath.push(new kakao.maps.LatLng(NW_link_list[i][j][1], NW_link_list[i][j][0]));
			}
			var polyline = new kakao.maps.Polyline({
				path: linePath, // 선을 구성하는 좌표배열 입니다
				strokeWeight: 5, // 선의 두께 입니다
				strokeColor: '#FF0000', // 선의 색깔입니다
				strokeOpacity: 0.7, // 선의 불투명도 입니다 1에서 0 사이의 값이며 0에 가까울수록 투명합니다
				strokeStyle: 'solid' // 선의 스타일입니다
			});

			// 지도에 선을 표시합니다 
			polyline.setMap(map);
		}
	&amp;lt;/script&amp;gt;
&amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;구체적으로 보자면, 파이썬을 실행시키면서 받아온 데이터를&lt;/p&gt;
&lt;pre id=&quot;code_1697100333201&quot; class=&quot;html xml&quot; data-ke-language=&quot;html&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;&amp;lt;script&amp;gt;
    var NW_link_list = {{ NW_link_list|tojson }};
&amp;lt;/script&amp;gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이 코드를 통해서 NW_link_list 라는 변수에 저장함. 여기 빨간줄 뜰텐데, 아무 문제 없으니 넘어가도 괜찮.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;가장 중요한 polyline을 찍는 js 코드.&lt;/p&gt;
&lt;pre id=&quot;code_1697100428775&quot; class=&quot;javascript&quot; data-ke-language=&quot;javascript&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;for (var i = 0; i &amp;lt; NW_link_list.length; i++) {
    var linePath = []; // 선을 구성하는 좌표 배열입니다. 이 좌표들을 이어서 선을 표시합니다
    for (var j = 0; j &amp;lt; NW_link_list[i].length; j++) {
        linePath.push(new kakao.maps.LatLng(NW_link_list[i][j][1], NW_link_list[i][j][0]));
    }
    var polyline = new kakao.maps.Polyline({
        path: linePath, // 선을 구성하는 좌표배열 입니다
        strokeWeight: 5, // 선의 두께 입니다
        strokeColor: '#FF0000', // 선의 색깔입니다
        strokeOpacity: 0.7, // 선의 불투명도 입니다 1에서 0 사이의 값이며 0에 가까울수록 투명합니다
        strokeStyle: 'solid' // 선의 스타일입니다
    });

    // 지도에 선을 표시합니다 
    polyline.setMap(map);
}&lt;/code&gt;&lt;/pre&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;여기서 NW_link_list 같은 경우, main.py 에 있는 print 주석을 해제한 후 보게되면,&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;[['127.08374812215546', '37.64624447253883'], ['127.08403711977205', '37.646315129324364']]&lt;/blockquote&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위의 값이 하나이다. 이 리스트에서 첫 번째 좌표(위도, 경도)와 두 번째 좌표를 이어서 link를 만든다는 의미이다.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;따라서 위 1번 코드와 비교해보았을 때, linePath 변수에 이 link를 모두 넣어주고,&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;link 값들이 들어간 linePath 라는 변수를 polyline 코드와 같이 작성해서 setMap 시켜준 것이다.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;실행시키면 아래와 같은 실행 화면을 볼 수 있을 것임. 실행 방법은 아래 참고&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;터미널 창에 입력. 경로는 myprj 에서 입력하기&lt;br /&gt;# 맥에서 실행: export FLASK_APP=main.py &amp;amp;&amp;amp; flask run&lt;br /&gt;# 윈도우에서 실행: set FLASK_APP=main &amp;amp;&amp;amp; $env:FLASK_APP = &quot;main.py&quot; &amp;amp;&amp;amp; flask run&amp;nbsp;&lt;/blockquote&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;윈도우에서 실행 시, &amp;amp;&amp;amp; 말고 한줄 씩 입력해주세요&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-filename=&quot;스크린샷 2023-10-12 오후 5.29.28.png&quot; data-origin-width=&quot;2290&quot; data-origin-height=&quot;2162&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cW3dwe/btsx47NDv9o/wLUvnGJoIk9oCK6oE6Vq3K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cW3dwe/btsx47NDv9o/wLUvnGJoIk9oCK6oE6Vq3K/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cW3dwe/btsx47NDv9o/wLUvnGJoIk9oCK6oE6Vq3K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcW3dwe%2Fbtsx47NDv9o%2FwLUvnGJoIk9oCK6oE6Vq3K%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;2290&quot; height=&quot;2162&quot; data-filename=&quot;스크린샷 2023-10-12 오후 5.29.28.png&quot; data-origin-width=&quot;2290&quot; data-origin-height=&quot;2162&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;+ 설명 부족한 부분이나 코드 실행 안되는 부분 댓글 남겨주세요.&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;[출처]&lt;/p&gt;
&lt;p style=&quot;background-color: #ffffff; color: #666666; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://apis.map.kakao.com/web/sample/drawShape/&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;https://apis.map.kakao.com/web/sample/drawShape/&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>FrontEnd</category>
      <author>혜원s</author>
      <guid isPermaLink="true">https://hyewon-s-dev.tistory.com/22</guid>
      <comments>https://hyewon-s-dev.tistory.com/22#entry22comment</comments>
      <pubDate>Thu, 12 Oct 2023 17:53:20 +0900</pubDate>
    </item>
  </channel>
</rss>