Skip to content

태그: TIL

총 863개의 글이 있습니다.
Scheduling Framework
node scheduling
Kubernetes Scheduling Framework는 kube-scheduler의 플러그인 기반 확장 메커니즘이다. 기존의 커스텀 스케줄링 방식들이 가진 한계를 극복하고, 유연하면서도 안정적인 확장성을 제공하기 위해 설계되었다. 등장 과정 Kubernetes에서 커스텀 스케줄링을 적용하기 위한 여러 시행착오가 있었다. Scheduler Extender 매 스케줄링마다 HTTP webhook을 호출하여 커스텀 결과를 받아오는 방식이다. 외부 서비스와의 HTTP 통신으로 인한 지연 발생 네트워크 장애 시 스케줄링 실패 가능성 Custom Scheduler 완전히 별도의 스케줄러를 띄우는 방식이다. 여러 스케줄러가 동시에 동작하면 race condition 발생 가능 따라서 Pod에 schedulerN
Data Lineage
db설계
데이터 리니지(Data Lineage)는 데이터가 어디서 와서 어디로 가는지 추적하는 것이다. 데이터 웨어하우스 등에서, 테이블이 많아지면 간접적으로 의존하는 테이블이 있을 수 있어 스키마 변경이 점점 어려워진다. 리니지가 있으면 이런 의존 관계를 한눈에 볼 수 있어서 영향 범위 파악이 훨씬 쉬워진다. 데이터 리니지를 설명할 때 A → B → C처럼 B 입장에서 A는 upstream(데이터 출처), C는 downstream(데이터 소비처)로 부르기도 한다. 리니지를 어느 방향으로 따라가느냐에 따라 forward lineage(downstream 방향, 영향도 분석)와 backward lineage(upstream 방향, 원인 추적)로도 나눈다. 테이블 리니지, 컬럼 리니지 테이블 단위 리니지는 “테이블 A
한국사능력검정시험
수학
1. 선사 문화와 국가의 형성 선사시대 구석기 동굴이나 막집, 주먹도끼, 슴베찌르개, 이동생활, 흥수아이(충북 두루봉 동굴) 신석기 모서리가 둥근 움집(화덕 중앙), 농경, 목축, 정착생활, 이른민무늬·빗살무늬토기 청동기 계급·재산, 고인돌, 직사각형 움집(화덕 한쪽 벽), 벼농사, 반달돌칼, 비파형동검 철기 세형동검, 철제농기구, 반량전, 명도전, 붓, 널무덤, 독무덤, 중국과의 교류 활발 연맹왕국 부여 사출도, 순장, 1책12법·형사취수제(고구려와 동일), 흰옷, 우제점복, 영고(12월) 부여엉고 고구려 제가회의, 상가·고추가·대로, 패자·사자·조의, 서옥제, 산악지대(약탈), 동맹(10월) 옥저 어물·소금(고구려에 공납), 민며느리제, 가족공동무덤,
Kafka 파티션 리더 선출
mq
Kafka는 분산 시스템이다. 파티션마다 리더가 있고, 리더만 읽기/쓰기를 처리한다. Kafka에서 각 파티션은 여러 브로커에 복제된다. 복제본(replica) 중 하나가 리더, 나머지는 팔로워다. 프로듀서와 컨슈머는 리더하고만 통신한다. 컨트롤러 컨트롤러라는 특별한 브로커 하나는 다음 역할들을 담당한다: 파티션 리더 선출 브로커 장애 감지 파티션 재할당 조율 컨트롤러 자체도 선출된다. 여러 브로커가 동시에 컨트롤러가 되려고 경쟁하고, 하나만 성공한다. ZooKeeper 모드에서는 /controller znode를 먼저 생성한 브로커가 컨트롤러가 된다. ephemeral node라서 해당 브로커가 죽으면 자동으로 삭제되고, 다른 브로커가 다시 경쟁한다. KRaft 모드에서는 Raft 합의 알고리즘으로
Aurora PostgreSQL CDC with DMS
database
PostgreSQL은 모든 변경사항을 WAL(Write-Ahead Log)에 먼저 기록한다. 이 WAL에는 물리적 변경(어떤 페이지의 어떤 바이트가 바뀌었는지)과 논리적 변경(어떤 테이블의 어떤 row가 INSERT/UPDATE/DELETE 되었는지) 정보가 모두 담겨 있다. Logical Replication은 이 WAL에서 논리적 변경만 추출해서 외부로 스트리밍하는 기능이다. 물리적 복제와 달리 테이블 단위로 선택적 복제가 가능하고, 다른 버전의 PostgreSQL이나 아예 다른 시스템(Kafka, DMS 등)으로 데이터를 보낼 수 있다. Replication Slot 그런데 한 가지 문제가 있다. WAL은 디스크 공간을 아끼기 위해 주기적으로 삭제된다. 만약 CDC consumer가 잠시 멈춰있는 동안
Session Affinity
개념
Session Affinity(세션 어피니티)는 특정 클라이언트의 요청이 항상 동일한 Pod로 라우팅되도록 하는 Kubernetes Service의 기능이다. “Sticky Session”이라고도 불리며, 상태를 유지하는 애플리케이션에서 세션 일관성을 보장하기 위해 사용한다. 기본 개념 기본적으로 Kubernetes Service는 요청을 모든 엔드포인트에 무작위로 분산한다. 이는 stateless 애플리케이션에는 문제가 없지만, 세션 상태를 메모리에 저장하는 애플리케이션에서는 문제가 된다. ┌──────────┐ ┌─────────────┐ ┌─────────┐│ │ ──▶ │ │ ──▶ │ Pod A │ 요청 1: 로그인 (세션 생성)│
Topology Aware Routing
개념
Topology Aware Routing은 Kubernetes Service의 트래픽을 가능한 한 같은 Zone(가용 영역) 내의 엔드포인트로 라우팅하는 기능이다. 클러스터가 여러 Zone에 걸쳐 배포되어 있을 때, 이 기능을 활성화하면 네트워크 지연 시간을 줄이고 Zone 간 데이터 전송 비용을 절감할 수 있다. 멀티 Zone 클러스터에서 Service로 요청이 들어오면, 기본적으로 kube-proxy는 모든 엔드포인트 중 하나를 무작위로 선택한다. 이 말은 Zone A에 있는 Pod가 Zone B나 Zone C에 있는 엔드포인트로 트래픽을 보낼 수도 있다는 것이다. ┌─────────────────────────────────────────────────────────────┐│
Linkerd와 Istio 비교
service mesh
Service Mesh는 마이크로서비스 간의 통신을 관리하는 인프라 계층이다. Kubernetes 환경에서 가장 많이 사용되는 Service Mesh인 Linkerd와 Istio의 구조와 특징을 비교해보자. Service Mesh가 필요한 이유 마이크로서비스 아키텍처에서는 수십, 수백 개의 서비스가 서로 통신한다. 이때 몇 가지 문제가 발생한다. 서비스 간 통신은 기본적으로 암호화되지 않는다. 어떤 서비스가 어떤 서비스와 통신하는지 파악하기 어렵다. 특정 서비스에 장애가 발생하면 연쇄적으로 다른 서비스에 영향을 미친다. 트래픽을 세밀하게 제어하기 어렵다. 이런 문제를 해결하기 위해 각 서비스에 프록시를 붙여서 모든 트래픽을 가로채고 관리하는 방식이 등장했다. 이것이 Service Mesh다. 그런데 Se
Gateway API
object
Gateway API는 Kubernetes에서 트래픽 라우팅을 관리하기 위한 차세대 API이다. 기존 Ingress의 한계를 극복하고 더 유연하고 표준화된 방식으로 L4/L7 트래픽을 관리할 수 있다. 왜 이런 변화가 필요했고, 어떤 구현체를 선택해야 할지 알아보자. Ingress의 한계 Ingress는 오랫동안 Kubernetes에서 외부 트래픽을 내부 서비스로 라우팅하는 표준이었다. 하지만 사용하다 보면 몇 가지 문제를 마주하게 된다. 프로토콜 제약 Ingress는 HTTP/HTTPS만 지원한다. TCP나 UDP 트래픽을 라우팅하려면 별도의 Service를 NodePort나 LoadBalancer로 노출해야 한다. gRPC도 직접적으로 지원하지 않는다. 어노테이션 지옥 Ingress 스펙 자체는 매우 단
PKI
응용
PKI(Public Key Infrastructure)는 공개 키 암호화를 실제 시스템에서 안전하게 사용할 수 있도록 만든 인프라이다. 공개 키 암호화는 수학적으로 안전하지만, 실제로 사용하려면 “이 공개 키가 정말 Alice의 것인가?”라는 질문에 답해야 한다. PKI는 이 문제를 중앙화된 신뢰 체계로 해결한다. 키 인증은 공개 키 암호화의 근본적인 문제이다. Bob이 Alice에게 암호화된 메시지를 보내려 한다고 하자. Bob은 Alice의 공개 키가 필요하다. 하지만 누군가 Alice의 공개 키라며 다른 키를 건네줄 수 있다. 이것이 중간자 공격(Man-in-the-Middle, MITM)이다. [정상적인 경우]Bob → Alice의 진짜 공개 키로 암호화 → Alice만 복호화 가능 [중간자 공격]B
Certificate Revocation
응용
인증서는 유효 기간이 있지만, 다음과 같은 이유로 만료 전에 폐기될 수 있다. 개인 키가 유출됨 인증서 정보가 변경됨 (회사명 변경 등) CA가 손상됨 도메인 소유권 변경 암호화 알고리즘 약화 인증서 폐기를 관리하는 방법에는 CRL, OCSP, OCSP Stapling, CRLite 등이 있다. Certificate Revocation List (CRL) CRL은 만료 전에 폐기된 인증서 목록이다. CA가 주기적으로 업데이트하여 배포한다. 클라이언트는 인증서를 검증할 때 CRL을 확인하여 폐기 여부를 체크한다. 실제 데이터는 아래와 같이 서명된 데이터 구조다. 발행자(Issuer): 이 CRL을 발행한 CA의 이름 발행 시각(This Update): CRL이 발행된 시각 다음 발행 시각(Next Upd
Certificate formats
응용
SSL 인증서 형식은 다양하지만, 모두 ASN.1(Abstract Syntax Notation 1) 형식 데이터를 기계가 읽을 수 있는 방식으로 인코딩하는 방법의 차이임. x509 인증서도 이 형식으로 정의됨. 기본 개념: ASN.1: 데이터 구조를 정의하는 표준 표기법 X.509: ASN.1로 정의된 공개키 인증서 표준 DER (Distinguished Encoding Rules): ASN.1을 바이너리로 인코딩하는 규칙 PEM: DER을 Base64로 인코딩하고 평문 앵커 라인 추가 정리하면, ASN.1 표기법을 사용하여 표시된 X.509인증서는 DER 인코딩을 통해 서명할 수 있는 바이트로 변환된다. 이는 사람이 쉽게 복사하거나 인식할 수 있는 텍스트가 아니므로 base64로 인코딩된다. 마지막으로
Keycloak
authentication
Keycloak은 ID 및 액세스 관리 솔루션을 제공하고, 인증(Authentication)과 인가(Authorization)을 쉽게 해주고 SSO(Single-Sign-On)을 가능하게 해주는 오픈소스이다. SSO란? SSO는 Single-Sign-On의 약자로 한번의 로그인을 통해 그와 연결된 여러가지 다른 사이트들을 자동으로 접속하여 이용할 수 있도록 하는 방법이다. 일반적으로는 여러 사이트를 사용할 떄 각각의 DB에 각각의 사용자 정보가 있고 그 정보를 통해서 관리를 하게 되는데, 필요에 따라서는 사용자 정보를 연동하여 사용해야 하는 경우가 발생한다. 이런 경우에 SSO 기능을 사용하게 되며 하나의 시스템에서 인증을 할 경우 그와 연결된 다른 시스템에서는 인증 정보가 있는지 없는지를 확인하여 이후 처
SSH
응용
SSH는 원격 서버에 안전하게 접속하기 위한 암호화 프로토콜이다. 공개키 인증의 원리 SSH는 비밀번호 대신 공개키 비대칭 암호화 방식을 사용한다. 따라서 두 개의 키를 사용한다. 개인키(Private Key): 절대 공유하지 않는 비밀 키 공개키(Public Key): 누구에게나 공개해도 되는 키 공개키로 암호화한 데이터는 개인키로만 복호화할 수 있다. 반대로 개인키로 서명한 데이터는 공개키로 검증할 수 있다. SSH 공개키 인증은 이렇게 작동한다. 클라이언트가 서버에 접속을 시도한다 서버는 등록된 공개키 목록(~/.ssh/authorized_keys)을 확인한다 서버가 무작위 챌린지 데이터를 생성해 클라이언트에게 보낸다 클라이언트는 개인키로 챌린지에 서명해 돌려보낸다 서버는 공개키로 서명을 검증한다
Noise
tls
Noise 프로토콜은 간단하고 안전한 암호화 통신을 위해 설계된 현대적인 핸드셰이크 프레임워크이다. Noise protocol framework는 핸드셰이크의 모든 협의를 피함으로써 TLS의 런타임 복잡성을 제거한 대안이다. TLS의 복잡한 협상 로직(cipher suite 선택, 프로토콜 버전 협상 등)을 제거하여 구현을 단순화한다. 사전에 정의된 패턴을 사용하므로 프로토콜 흐름이 명확하고 예측 가능하다. 노이즈를 실행하는 클라이언트와 서버는 분기하지 않는 선형 프로토콜을 따른다. TLS는 핸드셰이크 메시지에 포함된 정보에 따라 다양한 경로를 취할 수 있다(조건부 분기). Noise는 미리 정의된 패턴을 따르므로 실행 흐름이 선형적이고 단순하다. 이는 구현의 정확성을 높이고 보안 검증을 용이하
writeConcern
mongodb
writeConcern은 MongoDB에서 쓰기 작업이 몇 개의 노드에 복제되어야 성공으로 간주할지를 결정하는 설정들이다. writeConcern이 높으면 쓰기 지연(latency)이 증가하는 대신, write를 마칠 때 데이터가 안전하게 보관됨을 더 강하게 보장할 수 있다. w, wtimeout, r 세 필드를 설정할 수 있다. w (Write Acknowledgment) 쓰기 작업이 몇 개의 노드에 반영되어야 확인(acknowledgment)을 받을지 지정하는 옵션이다. 레플리카 셋의 노드 수보다 높은 w 값을 설정하면 쓰기가 실패한다. w: 0 쓰기 확인을 기다리지 않는다. 가장 빠른 성능을 제공한다. 네트워크 오류나 서버 장애 시 데이터 손실 가능성이 매우 높다. 로그나 임시 데이터처럼 손실
EthereumClient
블록체인
이더리움은 크게 세 가지 종류의 클라이언트 소프트웨어가 각자의 역할을 수행하며 상호작용하는 구조이다. Execution Client 실행 클라이언트는 이더리움의 상태(State)를 관리하고 트랜잭션을 실제로 처리하는 소프트웨어이다. 핵심 임무: 실행과 상태 관리 사용자가 보낸 트랜잭션(거래)을 실제로 실행하고, 스마트 컨트랙트 코드를 처리하는 역할을 전담한다. 이더리움의 현재 상태를 데이터베이스 형태로 꼼꼼하게 유지하고 계속 업데이트한다. 상태’정보란 다음을 포함한다: 모든 계정의 이더(ETH) 잔액 스마트 컨트랙트의 내부 저장 공간(데이터) 각 계정의 트랜잭션 횟수(논스, Nonce) 멤풀(Mempool) 관리 아직 블록에 포함되지 않은 트랜잭션들이 대기하는 공간(멤풀)을 관리한다. 나
CEX와 DEX
블록체인
암호화폐 거래소는 디지털 자산을 거래할 수 있는 플랫폼으로, 중앙화 거래소(CEX, Centralized Exchange)와 탈중앙화 거래소(DEX, Decentralized Exchange)로 나뉜다. CEX는 기업이 운영하며 사용자의 자산을 보관하지만, DEX는 스마트 컨트랙트를 통해 사용자가 직접 자산을 관리하며 P2P로 거래한다. 유동성과 슬리피지 거래소를 이해하려면 유동성과 슬리피지 개념을 먼저 알아야 한다. 유동성(Liquidity)은 시장에서 자산을 얼마나 쉽게 사고팔 수 있는지를 나타낸다. 유동성이 높다는 것은 원하는 가격에 즉시 거래할 수 있다는 뜻이고, 유동성이 낮으면 거래 상대방을 찾기 어렵거나 불리한 가격으로 거래해야 한다. 호가창에 매수/매도 주문이 빽빽하게 쌓여있으면 유동성이 높다
오일러 정리
정수론
오일러 피 함수 오일러 피 함수는 1~n 범위 중 n과 서로소인 숫자의 갯수를 구하는 함수이다. 1부터 6까지의 정수 중 6과 서로소인 수는 1, 5 두 개이므로 φ(6) = 2이다. 1부터 10까지의 정수는 모두 11과 서로소이고, 11은 자신과 서로소가 아니므로, φ(11) = 10이다. 1은 자기 자신과 서로소이므로, φ(1) = 1이다. 오일러 정리 오일러 정리는, 정수 a 및 양의 정수 n이 주어졌고 a와 n이 서로소일 때 아래 식이 성립한다는 내용이다. a^φ(n) ≡ 1 (mod n) 페르마 소정리와 유사한 논리로 증명할 수 있다. n과 서로소인 1부터 n까지의 정수를 r₁, r₂, …, r_φ(n)이라 하자. 이들의 개수가 바로 φ(n)개이다. a가 n과 서로소일 때, ar₁, ar
RSA
암호화
RSA는 Ron Rivest, Adi Shamir, Leonard Adleman에 의해 1977년 개발된 최초의 실용적인 공개 키 암호화 알고리즘이다. 두 큰 소수를 곱하는 것은 쉽지만, 그 결과를 소인수분해하는 것은 계산적으로 매우 어렵다는 수학적 난제를 기반으로 한다. 충분히 큰 키 크기를 사용하면 현재 알려진 알고리즘으로는 현실적인 시간 내에 해독이 불가능하다. 키 생성 과정 RSA 키 쌍을 생성하는 단계는 다음과 같다: 두 소수 선택 두 개의 큰 소수 p와 q를 무작위로 선택한다. 실제 사용에서는 각각 1024비트 이상의 소수를 선택한다. 모듈러스 계산 n = p × q를 계산한다. n은 공개 키와 개인 키 모두에 포함되는 모듈러스이다. 오일러 피 함수 계산 φ(n) = (p-1)
Stablecoin
블록체인
스테이블코인(Stablecoin)은 가격 안정성을 목표로 설계된 암호화폐로, 법정화폐, 상품, 또는 알고리즘을 통해 가치를 유지한다. 비트코인이나 이더리움과 같은 일반 암호화폐는 높은 변동성을 가지지만, 스테이블코인은 안정적인 가치를 제공하여 결제 수단, 가치 저장, 거래소 간 이동 등에 활용된다. 따라서 거래소 간 자금 이동 시 변동성 없이 빠르게 이전할 수 있다. 상거래 결제에 안정적으로 사용되며, 탈중앙화 금융(DeFi)에서 대출, 예금, 유동성 제공의 기초 자산으로 활용된다. 국경 간 송금에서 빠르고 저렴한 수단을 제공하고, 암호화폐 시장 변동성을 회피하기 위한 안전자산 역할도 한다. 법정화폐 담보형의 경우 실제 담보 보유 여부가 불투명할 수 있고, 각국 정부의 규제 변화에 민감하게 반
BFT
블록체인
비잔틴 장애 허용(Byzantine Fault Tolerance, BFT)은 분산 컴퓨팅 시스템에서 일부 노드가 악의적으로 행동하거나 임의로 실패하더라도 시스템이 합의에 도달하고 정상적으로 작동할 수 있는 능력이다. 이는 1982년 Leslie Lamport가 제시한 “비잔틴 장군 문제(Byzantine Generals Problem)“에서 유래했다. 비잔틴 장군 문제 여러 비잔틴 장군들이 도시를 포위하고 있고, 메신저를 통해 통신하며 공격 또는 후퇴를 결정해야 하는 상황이다. 문제는 일부 장군이나 메신저가 배신자일 수 있으며, 이들이 잘못된 정보를 전달할 수 있다는 점이다. 충성스러운 장군들은 배신자가 있더라도 동일한 작전 계획에 합의해야 한다. 신뢰할 수 없는 환경에서 합의가 필요한 다양한 시
Consensus mechanisms
블록체인
Consensus mechanism(합의 알고리즘)은 분산 네트워크에서 블록체인의 상태에 대해 모든 노드가 동의하도록 하는 메커니즘이다. Bitcoin에서 사용하는 Proof of Work 외에도 다양한 합의 메커니즘이 개발되어 사용되고 있다. Proof of Stake (지분 증명) Proof of Work에 대한 대안으로, 채굴의 필요성을 제거하여 작업 증명을 개선하는 것을 목표로 하는 합의 알고리즘이다. 암호화폐 보유자들은 의결권을 얻기 위해 잔고를 걸고(스테이킹) 거래를 검증하기 위해 네트워크에 의해 선택될 기회를 갖는다. 스테이킹을 통해 노드 또는 validator로서의 역할을 수행할 수 있다. 고가의 하드웨어 요구사항이나 어려운 계산 과정은 없지만 암호화폐 보유자들이 자금을 투입하는 데
ICO
블록체인
Initial Coin Offering (ICO)는 암호화폐 개발 업체에서 투자 자금을 모집하기 위해 자사에서 개발한 암호화폐의 일부를 현금이나 다른 암호화폐를 받고 넘겨주는 것이다. 미래에 상장될 코인의 가치를 약속하고 그보다 저렴한 환율로 현재의 자금을 환전해 주는 방식이다. 전통적인 기업공개(IPO)와 유사하지만, 주식 대신 암호화폐 토큰을 발행한다는 점에서 차이가 있다. ICO 방식이 처음으로 도입된 암호화폐는 이더리움이다. 개발자인 비탈릭 부테린은 백서(白書; whitepaper)를 공개하고 비트코인을 받아 개발에 필요한 자금을 확보했다. 이더리움이 성공적으로 개발되고 투자자들에게 배부된 ETH 토큰의 가치가 상승하자, 투자자들은 많은 이득을 보게 되었다. 이더리움의 성공 이후 수많은
Bitcoin Script
블록체인
비트코인 스크립트는 트랜잭션 출력의 사용 조건을 정의하는 스택 기반 프로그래밍 언어이다. ScriptPubKey와 ScriptSig 모두 같은 방식으로 파싱된다. 파싱을 시작하고 처음 읽은 한 바이트 값이 n이고 이 값이 0x010x4b(175) 사이의 값이면 n바이트 길이만큼 이어서 읽은 숫자를 한 원소로 간주한다. 그렇지 않으면 그 바이트 값은 오피 코드를 의미한다. 연산자, 오피코드 대응 표 비트코인의 스크립트에선 반복문을 허용하지 않는다. (튜링 완전하지 않다.) 튜링 완전한 스마트 계약 언어인 Solidity를 이용하는 이더리움은 gas라는 단위를 프로그램 실행 대가로 지불하도록 강제하여 해결한다. 거래를 하기 위해선 이전 트랜잭션의 해제 스크립트(ScriptPubKey)로 코
스마트 컨트랙트
블록체인
스마트 컨트랙트(Smart Contract)는 블록체인 상에서 자동으로 실행되는 프로그램으로, 계약 조건이 충족될 때 자동으로 실행되는 디지털 계약이다. 중개자 없이 신뢰할 수 있는 거래를 가능하게 하며, 투명성과 불변성을 보장한다. 역사적 배경 스마트 컨트랙트라는 용어는 1994년 미국의 컴퓨터 과학자 Nick Szabo가 처음 제안했다. 1996년 Szabo는 여러 논문을 발표하며 스마트 컨트랙트를 “계약 조건을 실행하는 전산화된 거래 프로토콜”로 정의했다. 그의 비전은 일반적인 계약 조건을 충족하고, 악의적이거나 우발적인 예외를 최소화하며, 신뢰할 수 있는 중개자의 필요성을 줄이는 것이었다. 자판기를 예시로 들어 설명했다: 동전을 넣으면 기계가 상품을 제공하는 방식처럼, 계약 당사자 간에 신뢰가 거의
서명과 영지식 증명
암호화
암호학에서는 서명을 Digital signature(디지털 서명) 또는 Signature scheme(서명 체계)이라 한다. 서명 체계는 일반적으로 다음 세 가지 알고리즘으로 구성된다. 서명자가 새로운 비밀키(서명키)와 공개키(검증키)를 생성하는 데 사용하는 키 쌍 생성 알고리즘 비밀키와 메시지를 사용하여 서명을 생성하는 서명 알고리즘 공개키, 메시지, 서명을 사용하여 성공 또는 오류 메시지를 반환하는 확인 알고리즘 서명은 메시지의 원본과 메시지의 무결성을 인증하는 데 유용하다. 원본(origin): 내 서명이 있는 경우 내가 보낸 것이다. 무결성(integrity): 누군가가 메시지를 수정하면 서명이 무효화된다. MAC에서 생성된 인증 태그는 타이밍 공격을 피하기 위해 상수 시간에 검
Alice and Bob
암호학
암호학 및 보안 프로토콜 설명 시 사용되는 관례적 이름이 있다고 한다. Alice: 첫 번째 참여자, 메시지나 암호화 키를 교환하려는 송신자 Bob: 두 번째 참여자, 메시지나 키를 수신하는 수신자 Carol/Carlos/Charlie: 세 번째 참여자, 다자간 통신이나 그룹 프로토콜에서 사용 Dan/Dave/David: 네 번째 참여자 Frank: 여섯 번째 참여자 공격자 Eve: 도청자, 수동적 공격자로 통신 엿듣기 가능하나 메시지 수정 불가 Michael/Mike: Eve의 대안, 마이크로폰에서 유래한 도청자 Niaj: 남아시아 국가에서 사용되는 Eve 대안 Mallory: 악의적 능동적 공격자, 메시지 수정/대체/재전송 가능, 중간자 공격에 사용, Mallet이나 Darth로도 불림 Trudy:
Kerckhoffs's principle
암호학
암호의 안전성은 알고리즘이 아니라 키의 비밀성에만 의존해야 한다. 암호화 알고리즘이 공개되어도, 키만 잘 지키면 안전할 수 있는 암호 체계를 만들어야 한다는 원칙이다. 우리가 어떤 암호화 알고리즘을 사용하고 있는지 공격자가 알고 있어도, 공격이 어려워야 한다. 이 원칙이 중요한 이유는 다음과 같다. 실제 환경에서는 알고리즘을 잘 안 바꾸고, 쓰던 것을 계속 사용하곤 한다. 키의 비밀성을 유지하는 것보다 알고리즘의 비밀성을 유지하는 것이 더 어렵다. 알고리즘이 공개되면, 더 많은 버그를 찾아내어 알고리즘을 개선시킬 수 있다. 이는 비공개 알고리즘을 상대적으로 신뢰하기 어려운 이유이기도 하다. 비밀이 적으면 적을수록 시스템은 안전하다. 우리가 실제 세계에서 배우고 사용하는 모든 암호화 알고리즘은
무작위성
암호학
보안 및 암호학 목적으로 난수가 필요하다면 난수는 예측할 수 없어야 한다. 애플리케이션은 일반적으로 무작위정을 운영체제에 의존하며, 운영체제는 실행되는 장치 유형에 따라 다른 트릭을 사용하여 무작위성을 수집한다. 무작위성의 일반적인 근원(entrypy source)은 하드웨어 인터럽트(마우스 움직임 등), 소프트웨어 인터럽트, 하드디스크 탐색 시간 등의 타이밍이 될 수 있다. 열 잡음과 같은 예측불가한 외부 물리현상으로 무작위적을 추출하는 하드웨어 난수 생성기를 진난수 생성기(TRNG, True random number generators)라고도 한다. 무작위성 추출기(randommness extractor)는 이런 여러 노이즈 소스를 정리하고 수집해야 한다. 허나 많은 난수를 빠르게 필요로
암호학
암호학
암호학의 분류 대칭 암호학(또는 비밀 키 암호학): 비밀 하나가 사용된다. 여러 참가자가 비밀을 알고 있는 경우 공유된 비밀이라고 한다. 비대칭 암호학(또는 공개 키 암호학): 참가자들은 비밀에 비대칭적인 관점을 가지고 있다. 예를 들어 일부는 공개 키를 알고 있고, 일부는 공개 키와 비밀 키 모두를 알고 있다. 암호학을 나누는 또 다른 방법은 다음과 같다. 수학 기반 구성: 인수 분해와 같은 수학적 문제에 의존한다. (예: 디지털 서명 및 비대칭 암호화를 위한 RSA 알고리즘) 휴리스틱 기반 구성: 암호 분석가의 관찰 및 통계 분석에 의존한다. (예: 대칭 암호화를 위한 AES) 참고 리얼월드 암호학 데이비드 웡
대칭암호화
암호화
AES (Advanced Encryption Standard) 현재 가장 널리 사용되는 대칭 암호화 표준이다. NIST에서 2001년 표준으로 채택되었으며, 이전 암호화 표준이었던 DES를 대체했다. 128비트의 평문을 128비트의 암호문으로 암호화한다. 고정된 크기의 평문을 암호화하기 때문에 블록 암호(Block cipher) 내부 동작 AES는 암호화 과정에서 평문의 state를 4*4 행렬로 본다. 여러 번 반복하는 라운드 함수에서, 라운드별로 (기본 대칭키에서 파생된) 각각 다른 라운드 키를 사용한다. 이를 통해 대칭 키의 비트를 약간만 변경함녀 완전히 다른 암호화가 가능하다 (확산 diffusion) 각 라운드엔 4개의 내부 단계가 있다. SubBytes: S-box를 사
비대칭암호화
암호화
비대칭 암호화는 공개 키와 개인 키라는 두 개의 서로 다른 키를 사용하는 암호화 방식이다. 공개 키로 암호화한 데이터는 개인 키로만 복호화할 수 있다. 공개 키는 안전하지 않은 채널로 전송해도 안전하다. n명이 통신하려면 n개의 키 쌍만 필요하다. (대칭 암호화는 n(n-1)/2개) RSA (Rivest-Shamir-Adleman) 1977년 개발된 최초의 실용적 공개 키 암호 시스템이다. 큰 소수의 곱셈은 쉽지만, 그 결과를 소인수분해하는 것은 계산적으로 어렵다는 원리를 이용한다. 키 생성 두 개의 큰 소수 p, q를 선택한다. n = p × q를 계산한다. (공개 모듈러스) φ(n) = (p-1)(q-1)을 계산한다. φ(n)과 서로소인 e를 선택한다. (공개 지수, 보통 65537
해시와 MAC
암호화
해시 함수 해시 함수는 데이터를 입력으로 받고 고유한 바이트 문자열을 생성한다. 출력을 다이제스트, 혹은 해시라고 한다. 해시의 특징 3가지가 있다. 역상 저항성(Preimage resistance): 역상(Preimage == y) 추측에 저항하는(Resistance) 성질 최초, 해시값(y)이 확인된 상태 입력값(x)을 찾는 것은 계산적으로 불가능 제2 역상 저항성(Second preimage resistance): 역상 추측에 저항하는 성질 최초, 입력값(x)이 확인된 상태 동일한 해시값(y)이 나오는 다른 입력값(x’)을 찾는 것은 계산적으로 불가능 충돌 저항성(Collision resistance): 서로 다른 입력값 추측에 저항하는 성질. 서로 다른 입력값은 동일한 해시값을
타원곡선
대수학
y^2 = x^3 + ax + b 그래프가 타원 모양은 아니고, 타원의 호 길이를 구하는 타원 적분의 역함수에서 나타나는 형태라 타원 곡선으로 불린다. 타원 곡선에서 점 덧셈: 곡선 위의 두 점에 대해 어떤 연산을 거쳐 곡선에 존재하는 제 3의 점을 얻는 과정 일반 덧셈 연산과 유사한 몇 가지 성질을 만족한다. 항등원 존재 (I + A = A가 되는 점 I, 무한원점이라 부름) 역원 존재 (A + (-A) = I임) 교환법칙 성립 결합법칙 성립 점 덧셈 공식 타원곡선 위의 두 점 P₁(x₁, y₁)과 P₂(x₂, y₂)에 대한 덧셈 P₃ = P₁ + P₂는 다음과 같이 계산된다. 경우 1: P₁ ≠ P₂인 경우 (점 덧셈) 결과 좌표 x₃ = s² x₁ x₂y₃ = s(x₁ x₃)
대수학
체 (Field): 덧셈과 곱셈이 정의된 집합으로, 다음과 같은 10가지 조건을 모두 만족하는 대수적 구조를 말한다. 가장 간단한 체의 예시로는 유리수의 집합 ℚ, 실수의 집합 ℝ, 복소수의 집합 ℂ가 있다. 반면 정수의 집합 ℤ나 자연수의 집합 ℕ은 체가 아니다. 어떤 집합 F가 체가 되기 위한 조건 덧셈 집합 F 안의 임의의 두 원소 a와 b를 더하면, 그 결과인 a + b도 반드시 F 안에 있어야 한다. (덧셈에 대한 닫힘성) 세 원소 a, b, c를 어떤 순서로 묶어서 더하더라도 결과가 같아야 한다. 즉, (a+b)+c = a+(b+c)이다. (덧셈의 결합법칙) 두 원소를 더하는 순서를 바꿔도 결과가 같아야 한다. 즉, a+b = b+a이다. (덧셈의 교환법칙) 어떤 원소 a에 더해도
HNSW
ai
HNSW는 고차원 벡터 공간에서 빠른 근사 최근접 이웃 검색을 위한 그래프 기반 알고리즘이다. 다층 그래프: Small World 네트워크 이론을 기반으로 여러 층으로 구성된다. Layer 0 (최하단층): 모든 벡터가 포함된 완전한 그래프 상위 층들: 확률적으로 선택된 일부 벡터들만 포함 각 층은 독립적인 연결 구조를 가진다. 장점 대용량 데이터에서 빠른 탐색 속도를 제공한다. 적은 메모리로 높은 성능을 달성한다. 실시간으로 벡터를 추가할 수 있다. 단점 정확한 최근접 이웃을 보장하지 않는다. 벡터 삭제가 복잡하다. 인덱스 구성에 시간이 소요된다. 세부 동작 삽입: 새 벡터를 인덱스에 추가하는 과정 지수 분포를 사용하여 새 벡터의 최대 층 수를 결정한다. 최상위 층의 진입
홀덤
알고리즘
홀덤(Hold’em)은 각 플레이어가 2장의 개인 카드와 5장의 공용 카드를 조합하여 최고의 패를 만드는 게임이다. 기본적인 텍사스 홀덤을 기반으로 다양한 변형 룰이 존재한다. 각 플레이어가 2장의 개인 카드(홀 카드)를 받는다 5장의 공용 카드(보드)가 단계적으로 공개된다 (플롭 3장 → 턴 1장 → 리버 1장) 개인 카드 2장과 공용 카드 5장 중 최적의 5장 조합으로 패를 만든다 프리플롭, 플롭, 턴, 리버 각 단계에서 베팅 라운드가 진행된다 최종적으로 가장 높은 패를 가진 플레이어가 승리한다 기본 용어 포지션 관련: 언더 더 건(UTG): 빅 블라인드 왼쪽 첫 번째 자리, 가장 불리한 포지션 버튼: 딜러 포지션으로 가장 유리한 자리, 모든 베팅 라운드에서 마지막에 행동 컷오프: 버튼 바로 왼쪽
Bloom filter
monitoring
Bloom Filter는 1970년 Burton Howard Bloom에 의해 고안된 공간 효율적인 확률적 데이터 구조로서, 어떤 요소가 집합에 속하는지를 테스트하는 데 사용된다. 이 구조의 핵심적인 특징은 false positive가 발생할 수 있지만, false negative는 발생하지 않는다는 점이다. 즉, Bloom Filter는 주어진 쿼리에 대해 “집합에 포함되어 있을 수도 있음” 또는 “집합에 확실히 포함되어 있지 않음” 중 하나의 결과를 반환한다. 충분한 메모리가 있다면 오류 없는 인덱스 해시를 사용할 수 있지만, 메모리가 제한적일 경우 Bloom Filter를 사용하는 것 만으로도 대부분의 디스크 접근을 불필요하게 만들 수 있다. Bloom Filter는 add only이고,
VictoriaLogs
victoria metrics
Loki는 Grafana에서 개발한 오픈소스 로그 관리 시스템이며, Elasticsearch나 OpenSearch 같은 기존의 오픈소스 로그 데이터베이스보다 RAM과 저장 공간을 적게 사용하는 것이 주요 장점이다. Loki는 전체 로그를 인덱싱하지 않고, 일부 로그 필드(로그 스트림 라벨)만 인덱싱하는 구조이기 때문에, 빠른 전체 텍스트 검색은 지원하지 않지만 라벨을 통한 빠른 로그 스트림 탐색은 가능하다. 로그를 압축 저장함으로써 저장 공간 효율이 높아지고, 이러한 아키텍처는 대량 로그 저장과 분석에 필요한 CPU, RAM, 스토리지 등의 인프라 비용을 절감할 수 있게 해준다. 그러나 Loki는 Elasticsearch와 비교했을 때 다음과 같은 단점을 가진다. 관리 측면 Loki는 구성
UPnP
l2 internet layer
Universal Plug and Play (UPnP)는 네트워크에 연결된 장치들이 자동으로 서로를 발견하고 통신할 수 있도록 지원하는 네트워크 프로토콜이다. 주로 가정용 네트워크 환경에서 사용되며, IP 기반의 네트워크에서 장치 간 편한 통신을 위해 설계되었다. 장치가 UPnP 네트워크에 연결되면, 다른 장치들에게 자신의 존재와 제공 가능한 서비스를 자동으로 알린다. NAT 환경에서 애플리케이션이 필요한 포트를 자동으로 열어, 사용자가 수동으로 설정할 필요를 줄인다. HTTP, XML, SOAP 등의 표준 인터넷 프로토콜을 기반으로 동작한다. 활용 사례 DLNA/UPnP 미디어 서버를 NAS나 공유기에 저장된 사진, 음악, 동영상을 스마트폰, 스마트 TV 등에서 스트리밍하는 용도로 활용할 수 있다.
CPU 아키텍처
cpu
Instruction Set Architecture ISA는 CPU가 이해하고 실행할 수 있는 명령어 집합이며, 특정 아키텍처의 하드웨어와 소프트웨어 간의 인터페이스이다. 각각의 CPU 아키텍처는 고유한 ISA를 가진다. 이 명령어 집합들은 운영체제와 어플리케이션에 사용된다. CPU 아키텍처 CPU의 설계와 명령어 집합(ISA)을 정의하는 방식이다. 아키텍처란 다른 하드웨어와 소프트웨어 간의 상호 작용을 가능하게 하는 인터페이스이다. CPU의 내부 구성 요소, 데이터 버스, 레지스터, ISA를 포함하는 시스템의 전반적인 구조와 동작을 나타내는 개념이고, ISA는 CPU가 이해하고 실행할 수 있는 명령어 집합을 정의하는 개념이다. 엄밀하게는 약간의 차이가 있지만 서로 교환 가능한 용어이다. CPU 아키
Resolution
영상
해상도(Resolution)는 영상의 가로 픽셀 수와 세로 픽셀 수를 의미한다. 예를 들어, 854x480은 가로 854픽셀, 세로 480픽셀로 구성된 화면이다. 해상도는 물리적으로 존재하는 픽셀 수만을 나타내며, 화면 비율(Aspect Ratio)과는 직접적으로 일치하지 않을 수 있다. SAR (Sample Aspect Ratio) 각 픽셀 하나의 가로 대 세로 비율을 뜻한다. SAR이 1:1이면, 하나의 픽셀은 정사각형이다. SAR이 1:1이 아닐 경우, 픽셀은 직사각형 모양이 되어 화면 전체에 왜곡을 발생시킨다. SAR은 인코딩 시점에 설정되며, 영상의 해석 방식에 영향을 준다. SAR을 조정함으로써, 같은 해상도를 유지하면서도 영상의 논리적 비율(DAR)을 수정할 수 있다. • 일부 문헌이
Instance Store
computing
AWS Instance Store는 Amazon Elastic Compute Cloud (EC2)에서 제공하는 임시 블록 수준 스토리지 서비스이다. EC2 인스턴스에 직접 연결된 로컬 디스크로, EC2 인스턴스가 실행 중인 동안에만 데이터를 유지한다. Instance Store는 인스턴스와 함께 묶여 있어 저렴하면서도 빠른 I/O 처리량을 제공한다. 그러므로 인스턴스 스토어를 사용하여 저지연 및 높은 처리량 작업을 수행할 수 있다. (대규모 데이터베이스, 데이터 웨어하우스, 로그 분석, 캐싱 등) 하지만 Instance Store는 휘발성이므로, 인스턴스가 종료되거나 재부팅되면 데이터가 영구적으로 삭제된다. 그러므로 임시 데이터나 캐시와 같이 데이터의 지속성이 필요하지 않은 작업에 적합하다. AWS Inst
RI와 Saving plan
computing
RI 예약 인스턴스(Reserved Instance)라고 한다. 1년 혹은 3년 동안 EC2 혹은 RDS 인스턴스의 특정 유형을 예약하여 사용하는 방법이다. 예를 들어, t2.micro 인스턴스 3개를 1년치 예약한다고 하자. 그럼 1년 동안은 실행 중인 t2.micro 인스턴스 3개에 대해 추가 비용 없이 사용할 수 있다(이미 비용을 지불했기 때문). 즉, 기존 t2.micro 인스턴스를 삭제하고 새로운 t2.micro 인스턴스를 생성해도 새로운 인스턴스는 자동으로 예약 인스턴스에 포함된다. 예약 인스턴스는 3가지 결제 방식을 지원한다. 전체 선결제(All Upfront) 비용을 모두 선결제, 가장 저렴하다. 부분 선결제(Partial Upfront) 일부는 선결제, 일부는 선결제 없음(No Upfro
Fault Injection Semulator
aws
AWS Fault Injection Simulator는 AWS에서 오류 주입 실험을 실행하기 위한 서비스로서 부하가 있을 때의 성능 테스트나, 특정 실패 이벤트에 대한 대처를 시뮬레이션해볼 수 있도록 한다. 테스트 결과를 통해 애플리케이션의 성능과 복원력을 개선시켜 애플리케이션이 예상대로 작동하도록 만들 수 있다. 실제 AWS 리소스에 대해 작업을 수행하기 때문에, 아무런 대비 없이 FIS를 돌리는 것은 서버 공격이나 다름없다. 꼭 자동 복구 작업 세팅 후 테스트하기 위해서 사용하자. Target으로 사용할 수 있는 서비스 목록 Amazon CloudWatch Amazon EBS Amazon EC2 Amazon ECS Amazon EKS Amazon RDS AWS Systems Manager Spot i
VPC Mapping Service
networking
AWS VPC를 이용해서 가상 네트워크를 만들면 아래와 같은 구성이 된다. 물리 Host 내에 다수의 VPC가 존재할 수 있고, 각 VPC 간에는 독립적인 구성이 가능하다. 각 VPC는 서로 다른 IP 대역(CIDR)를 사용하는 것 뿐 아니라, 내부 IP를 같은 값으로 지정할 수도 있다. 하나의 VPC는 여러 물리 Host로 나뉘어 위치하기도 한다. 서로 다른 Host에 위치한 ZIGI-VM1과 ZIGI-VM3은 논리적으로 같은 네트워크이기 때문에 서로 간의 통신이 가능하다. 근데 물리적으로 서로 다른 ZIGI-VPC1과 ZIGI-VM3은 어떻게 통신이 가능할까? 바로 아래과 같이 VPC에 대한 정보는 Encapsulation하고, 통신하고자 하는 물리 Host IP 정보를 같이 담아 전송하게 된다. 그
VPC
networking
가상 프라이빗 클라우드(VPC)는 퍼블릭 클라우드 내에서 호스팅되는 안전하고 격리된 프라이빗 클라우드이다. VPC를 사용하면 정의한 논리적으로 격리된 가상 네트워크에서 AWS 리소스를 효율적으로 관리할 수 있다. VPC별로 네트워크를 구성하거나 각각의 VPC에 따라 다르게 네트워크 설정을 줄 수 있다. 또한 각각의 VPC는 완전히 독립된 네트워크처럼 작동한다. 아래 그림은 VPC의 예시이다. VPC에는 리전의 각 가용성 영역에 하나의 서브넷이 있고, 각 서브넷에 EC2 인스턴스가 있고, VPC의 리소스와 인터넷 간의 통신을 허용하는 인터넷 게이트웨이가 있는 구조이다. 쉽게 예시를 들자면, 퍼블릭 클라우드를 붐비는 레스토랑으로, 가상 프라이빗 클라우드를 붐비는 레스토랑의 예약된 테이블로 생각해볼 수 있다.
Whisper
ai
OpenAI에서 공개한 Whisper는 다양한 언어를 인식할 수 있는 범용 음성 인식 모델이다. 입력으로 오디오 데이터를 받아 텍스트로 변환한다. 하지만 기본 Whisper 모델은 속도가 느리고 리소스를 많이 사용하는 단점이 있다. 이를 개선하기 위한 프로젝트들이 다음과 같다. ⸻ CTranslate2 CTranslate2는 Facebook의 fairseq에서 영감을 받아 만들어진 변환기(Transformer) 모델을 위한 고성능 추론 엔진이다. ONNX 모델을 최적화된 형식으로 변환한 후, CPU나 GPU에서 빠르게 실행할 수 있도록 설계되었다. Whisper의 디코더 부분이 Transformer 기반이기 때문에, Whisper 모델의 디코딩 속도를 빠르게 만들기 위해 CTranslate2가 사
Native messaging
개발
브라우저 Native Messaging은 확장 프로그램(Extension)이 외부 네이티브 애플리케이션과 직접 통신할 수 있도록 하는 기술이다. 보통 웹 브라우저 내에서 실행되는 확장 프로그램은 보안상의 이유로 로컬 파일이나 시스템 리소스에 직접 접근할 수 없다. 하지만, Native Messaging을 사용하면 브라우저 확장이 특정한 네이티브 애플리케이션을 실행하고 JSON 메시지를 주고받을 수 있다. Native messaging을 사용하면 브라우저 확장 플러그인에 아래 같은 기능을 추가할 수 있다. 파일 시스템 접근: 확장 프로그램에서 로컬 파일을 읽거나 쓰는 작업 수행 네이티브 애플리케이션 제어: 특정 데스크톱 애플리케이션을 실행하고 상태를 확인 보안 관련 작업: 키보드 보안, 암호 관리 소프트웨어
LSA와 LDA
자연어 처리
잠재 의미 분석(Latent Semantic Analysis, LSA) 잠재 의미 분석(Latent Semantic Analysis, LSA)은 자연어 처리 분야에서 문서와 단어 간의 숨겨진 의미 관계를 발견하기 위한 통계적 기법이다. 이는 주어진 문서 집합에서 단어들의 공동 발생 패턴을 분석하여, 단어와 문서 간의 잠재된 의미 구조를 파악하는 데 사용된다. LSA의 기본 개념 LSA는 다음과 같은 절차를 따른다: 문서-단어 행렬(DTM) 생성: 문서 집합에서 각 문서와 단어의 발생 빈도를 나타내는 행렬을 만든다. 특이값 분해(Singular Value Decomposition, SVD): DTM에 SVD를 적용하여 세 개의 행렬로 분해한다. 이를 통해 데이터의 차원을 축소하고 노이즈를 제거
t-value
통계학
검정 통계량 통계적 가설의 진위를 검정하기 위해 표본으로부터 계산하는 통계량이다. t-value, F-value, z-value 등이 바로 검정 통계량이다. 쉽게 말해, 표본 데이터를 이용해 세운 가설이 맞는지를 판단할 수 있는 도구라고 할 수 있다. t-value의 의미 t-value는 두 표본 집단의 차이를 평균을 중심으로 비교하며, 이를 불확실도로 나누어 계산한다. 이 값은 차이가 클수록, 불확실도가 작을수록 커지며, 통계적으로 유의미한 차이가 있음을 의미한다. t-value의 수학적 정의 두 집단의 평균 차이: ( \bar{X}_1 \bar{X}_2 ) 두 집단 평균 차이의 불확실도(표준 오차): ( s_{\bar{X}_1 \bar{X}_2} = \sqrt{s_1^2/n_1 + s_2^2/n
윌콕슨 순위합 검정
통계학
Frank Wilcoxon에 의해 고안된 윌콕슨 순위합 검정은 두 그룹 사이의 중앙값 차이를 비교하는 비모수 검정이다. 데이터가 정규분포를 따르지 않거나 이상치의 영향을 많이 받을 때 적합하다. t-검정과 다르게 데이터 분포에 덜 민감하다. 간단하면서도 효과적으로 두 그룹 간의 차이를 확인할 수 있는 방법이지만, 패턴을 충분히 반영하지 못할 가능성도 있기 때문에 다른 검정과 함께 고려하는 것이 좋다. 비모수 검정 데이터 분석에서는 다양한 통계 기법이 사용되는데, 그 중에서도 비모수(non-parametric) 통계 기법은 유연함과 실용성 면에서 큰 장점을 지닌다. 비모수 검정에선 데이터를 다룰 때 평균이 아닌 중앙값에 초점을 맞춘다. 정규성 가정을 하지 않아 다양하고 복잡한 데이터에 적합하다. 비슷한
rerere
git
git rerere는 비교적 장기간 유지되는 토픽 브랜치를 사용하는 워크플로우에서 동일한 충돌을 반복적으로 해결해야 하는 문제를 해결하기 위한 도구이다. 토픽 브랜치가 “release” 브랜치에 병합되거나 업스트림에 전송되어 승인될 때까지, 개발자는 종종 같은 충돌을 여러 번 해결해야 한다. 이 명령어는 최초 수동 병합 시 충돌이 발생한 자동 병합 결과와 그에 대응하는 수동 해결 결과를 기록하고, 이후 동일한 충돌이 발생했을 때 이전에 기록된 해결 방법을 자동으로 적용한다. 주의: 이 명령어를 사용하려면 rerere.enabled 설정 변수를 활성화해야 한다. 명령어 일반적으로 git rerere는 인자 없이 또는 사용자 개입 없이 실행된다. 하지만 작업 상태와 상호작용할 수 있는 여러 명령어를 제공한
비트레이트
영상
프레임 레이트 frame rate 프레임 레이트 단위는 fps(frame per second)이다. 30fps라면, 1초에 30장의 프레임이 재생된다. 초당 재생되는 이미지 수가 많아지면 동영상이 더 부드럽게 재생된다. 비트 레이트 bit rate 비트 레이트 단위는 bps(bits per second)이고, 초당 처리하는 데이터 크기를 의미한다. 동영상에서 화질은 해상도와 함께 비트레이트 크기가 중요한 역할을 한다. 해상도가 아무리 높아도 비트레이트가 낮으면 화면이 뭉개진다. 그렇다고 비트레이트를 무턱대고 높인다고 화질이 무조건 좋아지는 것도 아니라 해상도에 맞는 적당한 비트레이트를 선택해야 한다. 물론 비트레이트를 높이면 해상도에 따른 화질이 보장되기는 하는데, 비트레이트가 너무 높으면 쓸데 없이 동영상
컨테이너와 코덱
영상
컨테이너 포맷(Container Format) 앞서 말한 것처럼 동영상 확장자는 오디오, 비디오 데이터인 스트림(Stream)을 하나 이상 가지고 있는 보관함 역할을 하며 이를 컨테이너 포맷(Container Format) 혹은 래퍼 포맷(Rapper Format)이라 부른다. 스트림(Stream)은 데이터, 패킷, 비트 등 일련의 연속성을 갖는 흐름/데이터를 의미하는데 간단히 컨테이너가 가지고 있는 비디오, 오디오 데이터라 생각할 수 있다. 컨테이너가 가지고 있는 비디오, 오디오 스트림(Stream)들은 코덱(Codec)을 통해 가공된 데이터들이다. 왜 코덱을 통해 가공을 했을까? 코덱(Codec) 코덱은 코더(Coder)와 디코더(Decoder)의 앞글자를 딴 합성어로 용량이 큰 영상을 다른 곳으로 이동
datadog anomaly detection algorithms
datadog
Datadog은 Anormaly detection 기준 설정을 위해 최대 6주간의 데이터를 학습하고, 아래 세 알고리즘 중 하나에 따라 계산한다. Basic (기본) 반복적인 계절성 패턴이 없는 지표에 사용한다. 간단한 롤링 윈도우 분위수 계산으로 예상 값의 범위를 결정한다. 적은 양의 데이터를 사용하고 변화하는 조건에 빠르게 적응하지만, 계절적 동작이나 장기 추세를 반영할 수 없다. Agile (민첩) 계절성이 있고 변동이 예상되는 지표에 사용한다. 이 알고리즘은 지표 수준의 변화에 빠르게 적응한다. SARIMA 알고리즘의 견고한 버전으로, 직전의 과거 데이터를 예측에 반영하여 수준 변화에 대해 빠른 업데이트를 가능하게 한다. 단, 최근의 장기 지속 이상치에 대해서는 견고성이 떨어지는 단점이 있다.
EME
개발
EME(Encrypted Media Extension)의 약자로, DRM이 걸려있는 영상 컨텐츠를 사용자가 단말기에서 보안 프로그램 설치 없이 사용할 수 있게 해주는 기술이다. EME를 적용하기 위해선 아래 네 가지가 필요하다. 암호화된 영상이 저장되어있는 스토리지 서버 콘텐츠를 암호화된 형태로 저장하고, 재생시 영상을 반환한다. Shaka Packager와 같은 도구를 사용해 암호화할 수 있다. 복호화 키가 들어있는 라이센스 서버 콘텐츠 재생에 필요한 암호화 키를 안전하게 발급한다. 인증서 영상을 복호화할 때, 복호화키와 인증서를 같이 가져와 인증해야한다. 이 인증서는 개인적으로 발급받기 어렵다. 따라서 인증서를 생성하여 나눠주는 Pallycon 등의 서비스를 사용할 수 있다.
CNN
ai
CNN이 나오기 이전, 이미지 인식은 2차원으로 된 이미지(채널까지 포함해서 3차원)를 1차원배열로 바꾼 뒤 FC(Fully Connected)신경망으로 학습시키는 방법이었다. 단순 FC 방식은 위와 같이 이미지의 형상을 고려하지 않고, raw data를 직접 처리하기 때문에 많은 양의 학습데이터가 필요하고 학습시간이 길어진다. 또한 이미지가 회전하거나 움직이면 새로운 입력으로 데이터를 처리해줘야 한다. 이미지의 특성을 이해하지 못하고 단순 1D 데이터로 보고 학습을하는것이 특징이다. 이러한 방법은 이미지 데이터를 평면화 시키는 과정에서 공간정보가 손실될 수밖에 없다. 즉, 신경망이 특징을 추출하고 학습하는데 있어 비효율적이고 정확도를 높이는데 한계가 있다. 이런 단점을 보완하여 이미지의 공간정보를 유
Keras
ai
케라스 케라스는 파이썬으로 구현된 쉽고 간결한 딥러닝 라이브러리로, 내부적으로 텐서플로우Tensorflow, 티아노Theano,CNTK 등의 딥러닝 전용 엔진이 구동되지만 내부엔진을 알 필요 없이 직관적인 API로 쉽게 다층퍼셉트론 신경망 모델, 컨벌루션 신경망 모델, 순환 신경망 모델 등 다양한 구성을 할 수 있다. 케라스의 가장 핵심적인 데이터 구조는 바로 모델이다. 케라스에서 제공되는 시퀀스 모델을 사용하면 원하는 레이어를 쉽게 순차적으로 정의할 수 있고, 다중 출력과 같이 좀 더 복잡한 모델을 구성하려면 케라스 함수 API를 사용하면 된다. 케라스로 딥러닝 모델을 만들 때는 다음과 같은 순서로 작성한다. 과정설명데이터셋 전처리원본 데이
Optimizer
ai
손실함수를 줄여나가면서 학습하는 방법은 여러가지가 있는데, 이를 최적화 하는 방법들을 Optimizer라고 부른다. 경사 하강법 경사하강법은 손실 함수또는 비용 함수라 불리는 목적 함수를 정의하고, 이 함수의 값이 최소화되는 파라미터를 찾는 방법이다. 손실 (loss) : 실제값과 모델로 예측한 값이 얼마나 차이가 나는가를 나타내는 값으로, 손실이 작을수록 예측값이 정확한 것이다.비용(cost, error)은 손실을 전체 데이터에 대해 구한 경우이며 비용을 함수로 나타낸 것을 손실 함수또는 비용 함수라고 한다. 함수의 최소값을 찾기 위해 임의의 위치에서 시작해서 기울기를 따라 조금씩 더 낮은 위치로 내려가며 극값에 이를 때까지 반복시킨다. 손실 함수는 인공지능의 파라미터를 통하여 나온 예측 값과 실제 값
RAG
ai
RAG(Retrieval-Augmented Generation)는 대규모 언어 모델의 출력을 최적화하여 응답을 생성하기 전에 학습 데이터 소스 외부의 신뢰할 수 있는 지식 베이스를 참조하도록 하는 절차이다. Advanced RAG 단순히 문서를 조회 -LLM 응답을 하는 Naive한 기본 RAG에서, 아래 방법들을 적용해 답변 품질을 개선할 수 있다. 메타데이터 활용 데이터에 대한 추가적인 정보를 제공하여 검색 결과의 정확도를 높인다. 고도화된 Chunking 전략 semantic chunking: 문맥적으로 관련된 내용을 하나의 청크로 묶는다. small to big: RAG에서 Chunk 를 retrieval 할때, 그 Chunk의 위와 아랫부분을 확장해서 같이 리턴하는 방법으로, 더 상세한 컨택
RNN
ai
은닉층 안에 하나 이상의 순환 계층을 갖는 신경망 기존 신경망 구조: 모든 입력과 출력이 각각 독립적이라 가정하고, 시간에 따른 입출력 간의 관계를 고려되지 않았음 RNN은 현재 입력을 유추할 때 이전 결과를 반영하여 계산하기 때문에 시간적 순서를 가지는 Sequence 기반 데이터, 연속적인 시계열(time series) 데이터를 잘 다룸 시간 순서를 기반으로 데이터들의 상관관계를 파악해서 그를 기반으로 현재 및 과거 데이터를 통해서 미래에 발생될 값을 예측 활성화 함수로 탄젠트 하이퍼볼릭을 많이 사용함 Cell 안에 Unit이 여러개 들어가고, 각 Cell마다 은닉상태를 가짐 유형 영향을 주는 셀과 영향받는 셀의 관계에 따라 One-to-One, One-to-Many, Many-to-Many 등으로
Vector Search
vector search
벡터 검색은 데이터의 의미를 기반으로 결과를 반환하는 검색 방법이다. 텍스트 일치를 찾는 기존 전체 텍스트 검색과 달리 벡터 검색은 다차원 공간에서 검색 쿼리에 가까운 벡터를 찾는다. 벡터가 쿼리에 가까울수록 의미가 더 유사하다. 벡터 검색을 통해 검색어와 데이터의 의미를 해석함으로써 검색자의 의도와 검색 컨텍스트를 고려하여 보다 관련성이 높은 결과를 검색할 수 있다. 벡터는 데이터를 여러 차원으로 나타내는 숫자 배열이다. 벡터는 텍스트, 이미지, 오디오, 구조화되지 않은 데이터까지 모든 종류의 데이터를 나타낼 수 있다. 의미적 유사성은 벡터 사이의 거리를 측정하여 결정된다. 과정 벡터 임베딩: vector embedding 데이터의 의미있는 특징을 벡터로 나타낸다. 유사도 점수 계산: similar
임베딩
embedding
임베딩은 자연어의 통계적 패턴을 숫자 벡터로 바꾼 결과이다. 고려하는 정보 임베딩을 만들 때 쓰는 통계 정보는 크게 세 가지가 있다. 첫째는 문장에 어떤 단어가 많이 쓰였는지이고, 둘째는 단어가 어떤 순서로 등장하는지이며, 마지막은 문장에 어떤 단어가 같이 나타났는지와 관련한 정보다. 백오브워즈(bag of words) 가정 수학에서 bag이란 중복 원소를 허용한 집합을 뜻한다. 백오브워즈 가정에서는 어떤 단어가 많이 쓰였는지 정보를 중시하고, 단어의 등장 순서는 무시한다. 단어 빈도 또는 등장 여부를 그대로 임베딩을 쓰는 것은 문서의 주제를 반영하지 못 할 수도 있다는 단점이 있다. (e.g. 은, 는과 같은 조사는 문서의 주제와 상관 없이 자주 등장) 이러한 단점을 보환하기 위해 TF-IDF(Ter
BERT
자연어 처리
BERT는 트랜스포머를 이용하여 구현되었으며, 위키피디아(25억 단어)와 BooksCorpus(8억 단어)와 같은 레이블이 없는 텍스트 데이터로 사전 훈련된 언어 모델이다. 구글이 2018년 공개하였다. BERT가 높은 성능을 얻을 수 있었던 것은, 레이블이 없는 방대한 데이터로 사전 훈련된 모델을 가지고 레이블이 있는 다른 작업(Task)에서 추가 훈련과 함께 하이퍼파라미터를 재조정하였기 때문이다. 넓은 범위에 대해 학습한 모델을 기반으로 다른 작업에 대해서 파라미터 재조정을 위한 추가 훈련 과정을 거치는 것을 파인 튜닝(Fine-tuning)이라고 한다. 스팸 메일 분류를 하고 싶다고 할때, 이미 위키피디아 등으로 사전 학습된 BERT 위에 분류를 위한 신경망을 한 층 추가한다. 이 경우, 비유하자면 B
Web Vitals
seo
웹 바이탈(Web Vitals)은 웹페이지 유저들의 사용 경험을 측정하는 구글의 표준화된 웹 성능 측정 기준이다. 사이트의 전반적인 로딩 속도, 상호작용, 웹페이지의 시각적 안정성, 보안 문제 등 여러 요소를 포함하고 있으며, 웹 사이트가 검색 엔진 결과에 표시되는 위치에 영향을 미친다. 검색 엔진에서 최적화하고 전체적으로 유저에게 좋은 환경을 제공하려면 코어 웹 바이탈을 개선해야한다. 성능 지표 중 주요항목으로는 6가지가 있다. FCP (First Contentful Paint) : 첫번째 텍스트 또는 이미지가 표시되는 시간 TTI (Time to Interactive) : 사용자 인터렉션이 가능해질 때까지 걸리는 시간 SI (Speed Index) : 페이지 속도. 얼마나 빨리 표시되는지 TBT (T
sitemap
seo
sitemap.xml 사이트맵은 사이트의 페이지, 동영상, 기타 파일들의 관계에 대한 정보를 제공하는 파일이다. 검색엔진 크롤러는 자동으로 홈페이지에서 시작하는 링크를 따라가 페이지를 탐색하는데, 홈페이지에서 모든 페이지를 접근할 수 없거나 페이지 갯수가 많은 경우(약 500개 이상) sitemap.xml 파일을 설정해놓으면 크롤러가 사이트를 더 효율적으로 크롤링할 수 있다. 사이트에 리치 미디어 콘텐츠(동영상, 이미지)가 많거나 Google 뉴스에 표시되어야 하는 경우 sitemap 파일로 추가 정보를 제공하는 것이 좋다. 크롤러에서 인식할 수 있는 사이트맵 형식은 여러가지가 있다. 사이트맵 형식장점단점XML 사이트맵URL에 대한 가장 많은 정보
ip_forward와 rp_filter
network
ip_forward IP forward는 일반적인 라우터 동작처럼 하나의 인터페이스로 들어온 패킷을 읽어서 일치하는 서브넷을 가지는 다른 네트워크 인터페이스로 패킷을 포워딩하는 것을 말한다. 라우터는 이 방식으로 패킷을 라우팅하지만 대부분의 호스트는 이 작업을 수행할 필요가 없다. 따라서 기본적으로 비활성화 되어있는 기능인데, 필요에 따라 옵션을 활성화할 수 있다. sysctl -w net.ipv4.conf.default.rp_filter=integersysctl -w net.ipv4.conf.all.rp_filter=integer interger에 활성화 여부를 나타내는 숫자를 넣는다. 0 비활성화 (기본값) not 0 활성화 인터페이스별로 지정해줄 수도 있다. sysctl -w net.ipv4.co
DERP
network
private 통신을 위해 UDP 포트를 열어놓고 STUN과 ICE를 사용하여 통신하는 경우가 있다. 하지만 이 방법은 필요한 커넥션의 갯수만큼 많은 포트를 열어놓아야 하기 때문에, Tailnet에선 보안적으로 더 우수한 DERP(Designated Encrypted Relay for Packets) 라는 방법을 사용한다. DERP는 각 수신자에게 가장 가까운 DERP를 통해 트래픽을 비대칭적으로 라우팅한다. Tailscale 개인 키는 생성된 노드를 절대 떠나지 않는다. 이는 DERP 서버가 귀하의 트래픽을 해독할 수 있는 방법이 전혀 없다는 것을 의미한다. 단지 이미 암호화된 트래픽을 한 노드에서 다른 노드로 맹목적으로 전달할 뿐이다. 이는 남용을 방지하기 위해 약간 더 고급 프로토콜을 사용하기는 하지만
pgbouncer
데이터베이스
Session 모드, Transaction 모드 PgBouncer를 비롯한 Database Proxy에는 커넥션 풀을 사용하는 모드가 크게 두 가지 있다. Session 모드 클라이언트가 PgBouncer에 맺는 커넥션과 PgBouncer에서 DB에 맺는 커넥션을 1:1 대응하여 실행하는 모드 세션 풀을 PgBouncer에서 관리하여, 기존보다 더 안정적인 풀링을 할 수 있다는 장점이 있다. Transaction 모드 클라이언트에서 실행하는 트랜잭션별로 pgbouncer 풀의 커넥션을 배정받아 실행하는 모드 생성된 커넥션이 낭비될 가능성을 줄이기 때문에, 총 커넥션 갯수를 더 적게 유지할 수 있다. 각 애플리케이션에서 가지고 있는 커넥션 수의 합이 실제 db 커넥션 수보다 적을 수 있다.
Domain-based Split Tunnels
network
VPN을 구성할 때, 특정 도메인에 대해서만 VPN을 활성화하고 싶은 경우가 있을 수 있다. 해당 기능에 대해 TailScale과 Netbird는 아래와 같은 방식으로 제공한다. TailScale에서 제공하는 방식 (문서) DNS 쿼리를 로컬 TailScale 서버로 날리도록 한다. 로컬 데몬에서는 8.8.8.8과 같은 도메인 서버에 다시 요청을 날려서, 도메인 쿼리 결과를 기록해놓은 후 결과를 그대로 돌려준다. 기록한 IP에 대해 커넥터로 지정된 호스트에 라우팅하도록 한다. private 네트워크에 성공적으로 통신할 수 있다. Netbird에서 제공하는 방식 VPN 클라이언트에서 도메인 쿼리 결과를 주기적(기본 60s)으로 불러와 기록해놓는다. 저장된 IP 목록에 해당하는 요청이 발생하면 Netbir
WebRTC
network
WebRTC(Web Real-Time Communication)란 웹 애플리케이션과 사이트가 중간자 없이 브라우저 간에 오디오나 영상 미디어를 스트림 하거나, 데이터를 자유롭게 교환할 수 있도록 하는 기술이다. 한마디로 요약하자면 드라이버나 플러그인 설치 없이 웹 브라우저 간 P2P 연결을 통해 데이터 교환을 가능하게 하는 기술이다. WebRTC는 기존의 웹 2.0에서 한층 더 나아가, 서버와 같은 중간자를 거치지 않고 브라우저 간을 P2P로 연결하는 기술이다. 화상 통화와 실시간 스트리밍, 파일 공유, 스크린 공유 등의 기능을 WebRTC 기반으로 구현할 수 있다. P2P 연결은 중개 서버를 거치지 않기 때문에 빠른 속도가 보장되며, HTTPS가 강제되기 때문에 중간자 공격에 대한 보안이 보장된다. Web
VPN
vpn
VPN이란 가상사설망이다. TCP/IP 기반의 개방형 네트워크인 인터넷에서 한 네트워크에서 다른 네트워크로 이동하는 모든 데이터 정보를 암호화하여 사설망 기능을 제공하기 위해 도입된 기술이다. 즉, 원격지에서 특정 네트워크(서버)와 마치 유선으로 연결된 것처럼 연결하는 것이다. VPN 터널은 암호화되기 때문에 해킹을 당했을 시에도 통신 데이터를 보호할 수 있다. VPN의 종류는 대표적으로 IPsec VPN, SSL VPN이 있다. IPsec VPN IPsec VPN은 VPN 게이트웨이(서버) 장비 2개를 서로 연결함으로써 네트워크와 네트워크를 연결하는 VPN이다. 기업의 본사 네트워크와 지사 네트워크를 연결하는 용도로 주로 사용된다. IPSec VPN을 IPSec VPN이라 부르는 이유는 VPN 터널을 생성
Wireguard와 Firezone
vpn
WireGuard WireGuard는 두 지점(Peer) 사이의 통신을 암호화하는 프로토콜에 대한 구현체이다. WireGuard는 Diffie-Hellman(DH) key 교환 방식을 기초로 하는 Noise protocol을 기반으로 만들어졌다. 특징 우수한 성능: UDP만을 사용하며, 불안정한 연결 환경에서도 잘 작동하도록 설계되었다. 또한 Linux에 내장되어 있는 암호화 기법들을 사용하면서 잘 최적화되어 있어 암호화 성능도 좋고, 모바일이나 임베디드 환경에서도 사용하기 좋다. 첨단 암호화 기법 사용: 안전하고 빠른 암호화 기법을 사용한다. WireGuard에서 내부적으로 사용하는 Noise protocol framework는 Zero round trip, forward secrecy 등을 지원하
New Architecture
react native
JIS 맨 처음엔 RN에서 js 엔진으로 JSC(Apple에서 만든, safari에서 쓰이는 엔진)가 사용되었는데, 브릿지의 책임이 커지고 서로 강결합된다는 문제가 발생했다. 이러한 문제를 해결하기 위해 엔진 인터페이스(JSI)가 만들어졌다. JIS는 Native와 JS 코드가 직접 상호작용할 수 있도록 한다. 즉 JSI라는 인터페이스를 통해서 자바스크립트가 호스트 쪽 객체의 레퍼런스를 직접 가질 수 있도록, 그리고 호스트 쪽 메소드도 직접 호출할 수 있도록 한다. 데이터 전달 과정 네이티브 모듈 인프라로 전달 js runtime이 c++로 전해주고, 네이티브 모듈 인프라로 전해서 처리 뷰도 같은 식으로 전달해서 UI Manager로 전해서 처리 (메모리 업데이트 되면 JS에 반영이 되어서 표시
React Native
react native
리액트 네이티브는 iOS와 안드로이드에서 동작하는 네이티브 모바일 앱을 만들기 위한 자바스크립트 프레임워크이다. 리액트 네이티브의 동작 원리는 리액트의 가상(virtual) DOM과 관련되어 있습니다. DOM 수정은 매우 값비싼 동작이기 때문에 리액트는 페이지의 변화를 바로 렌더링 하는 대신 메모리의 가상 DOM을 이용해 변화가 필요한 곳을 계산하고 최소한의 변경사항만 렌더링한다. 리액트 네이티브는 같은 원리를 이용해 브라우저의 DOM이 아닌 오브젝티브-C API를 호출하여 iOS 컴포넌트를 렌더링하고, 자바 API를 호출하여 안드로이드 컴포넌트를 렌더링한다. 이는 브릿지가 대상 플랫폼의 네이티브 UI 요소에 접근하는 인터페이스를 제공하기 때문에 가능하다. 스레딩 모델 리액트 네이티브는 다음의 다중 스레드
GC
go
Go의 GC는 mark-sweep 방식으로 동작하며 두 가지 주요 단계로 나뉜다. 마킹: 메모리에서 살아있는 객체를 식별한다. 스윕: 죽은 객체를 해제하여 메모리를 반환한다. GC는 스윕 → 비활성 → 마킹 세 단계를 순회하며 주기적으로 진행된다. Go의 GC는 현시점의 Heap 크기와 직전 시점의 Heap 크기에 대한 증가율이 특정 정도에 다다르면 수행되는 로직으로 구현되었다. 이 때 그 정도를 정하는 변수는 GOGC라고 부른다. GOGC 값을 사용해 아래와 같이 목표 힙 메모리를 구한다. 목표 힙 메모리 = 살아있는 힙 메모리 + (살아있는 힙 메모리 + GC 루트) × GOGC / 100 예를 들어, 살아있는 힙이 8 MiB이고, GOGC가 100일 때, 목표 힙 메모리는 18 MiB이다. GO
slice
go
슬라이스는 내부적으로 사용하는 배열의 부분 영역인 세그먼트에 대한 메타 정보를 가지고 있다. 슬라이스는 크게 3개의 필드로 구성되어 있다. 내부적으로 사용하는 배열에 대한 포인터 정보 세그먼트의 길이 세그먼트의 최대 용량(Capacity) append append()가 슬라이스에 데이터를 추가할 때는 슬라이스 용량(capacity)이 아직 남아 있는 경우: 용량 내에서 슬라이스의 길이(length)를 변경하여 데이타를 추가한다. 용량(capacity)을 초과하는 경우: 현재 용량의 2배에 해당하는 새로운 Underlying array를 생성하고, 기존 배열 값들을 모두 새 배열에 복제한 후 다시 슬라이스를 할당한다. 아래 예제는 길이 0, 용량 3의 슬라이스에 1부터 15까지의 숫자를 계속 추가하면
LSM Tree
자료구조
LSM 트리는 로그파일 기반으로 작성되는 방식의 파일 구조이다. LSM 트리는 Append-only 방법이어서 쓰기작업의 효울성이 좋다. 작동 방식 쓰기 작업 LSM 트리는 데이터를 disk에 바로 쓰지 않고, 정렬된 메모리 테이블(memTable)과 로그파일에 먼저 쓴다. 메모리 테이블은 주로 레드-블랙 트리를 사용하여 키-값 쌍을 기반으로 정렬된 구조를 유지한다. Memtable이 설정된 임계값에 도달하면, 그 내용은 디스크에 파일로 저장됩니다. 이때 데이터는 정렬된 상태로 저장되기 떄문에, 이 파일을 SSTable(Sorted String Table)이라고 부른다. SSTable은 불변성을 지니며, 한 번 기록된 후에는 변경되지 않는다. 이 구조는 데이터 일관성을 보장하며 압축이 진행되는 중에도
MongoDB Aggregation
mongodb
MongoDB의 Aggregation은 각 스테이지가 순차적으로 처리되며, 그 결과를 다음 스테이지로 전달하면서 사용자의 요청을 처리한다. 그래서 각 스테이지들의 배열 순서는 처리 성능에 많은 영향을 미친다. 예를 들어, 필요한 도큐먼트만 필터링 하는 스테이지는 데이터를 그룹핑하는 스테이지보다 앞쪽에 위치해야 그룹핑해야 할 도큐먼트의 건수를 줄일 수 있고, Aggregation의 성능을 높일 수 있다. aggregation 파이프라인의 각 단계에서는 다음과 같은 연산자들을 제공한다. $project: 출력 도큐먼트상에 배치할 필드를 지정한다. $match: 처리될 도큐먼트를 선택하는 것. find()와 비슷한 역할을 수행한다. $limit: 다음 단계에 전달될 도큐먼트의 수를 제한한다. $skip: 지정된
Atlas Search
mongodb
MongoDB의 Atlas Search는 Atlas 클러스터에서 데이터의 세밀한 텍스트 인덱싱과 쿼리를 가능하게 한다. Atlas Search는 데이터베이스에 별도의 검색 시스템을 추가하지 않고도 고급 검색 기능을 사용할 수 있도록 한다. Atlas Search는 여러 종류의 텍스트 분석기 옵션, $search와 $searchMeta 같은 Atlas Search 집계 파이프라인 단계를 다른 MongoDB 집계 파이프라인 단계와 함께 사용하는 풍부한 쿼리 언어, 그리고 점수 기반 결과 순위 지정을 제공한다. 개념 인덱싱 검색에서 인덱스는 쉽게 검색할 수 있는 형식으로 데이터를 분류하는 데이터 구조다. 검색 인덱스는 전체 컬렉션을 스캔하지 않고도 주어진 용어를 포함하는 문서를 더 빠르게 검색할 수 있게 한다.
Trie
자료구조
트라이는 문자열을 저장하고 효율적으로 검색하기 위한 트리 기반의 자료구조이다. 트라이는 루트 노드부터 시작하고, 각 노드는 문자를 나타낸다. 그리고 문자열은 루트에서 리프 노드까지의 경로로 표현된다. 트라이 자료구조를 사용하면 문자열을 매우 빠르게 검색할 수 있다. 특히 접두사 검색에 효율적이다. (O(m) 시간, m은 문자열 길이). 큰 메모리가 필요하다는 단점이 있다. 접두사를 바탕으로 한 자동 완성이나, 문자열 매칭을 위해 사용할 수 있다. 구현 트라이의 한 노드를 구성하는 객체는 자손 노드를 가리키는 포인터 목록과, 문자열의 끝인지를 나타내는 bool 변수로 구성된다. 자손 노드 포인터를 저장하기 위해 맵이나 벡터를 사용할 수 있다. struct Trie { map&x3C;char, Trie*>
SLO, SLI, SLA
monitoring
SLA: Service Level Agreements SLA는 고객이 서비스를 사용할 때 기대하는 서비스 레벨이다. SLA를 정의할 떄는 단순한 지표를 사용하는 것이 좋다. SLO: Service Level Objectives SLO란 시스템에서 기대하는 가용성을 설정한 목표이다. SLA가 사용자가 기대하는 수치라면, SLO는 실제로 팀에서 지키기 위해 노력할 달성 목표이다. SLO는 발생할 수 있는 변수를 감안하여 SLA보다 더 높은 값으로 설정하는 경우가 많다. 목표에 집중하기 위해선 SLO는 최소 갯수만 정의하는 것이 좋다. SLI: Service Level Indicator SLI란 사용자가 시스템의 가용성을 경험하는 방식을 정량적으로 측정한 것이다. 즉, 목표에 대비한 실제 지표이다. SL
임베디드 리눅스 프로그래밍 수업 정리
embedded
임베디드 시스템의 특징 임베디드 시스템: 내부에 Computer(마이크로 프로세서/마이크로 컨트롤러)를 내장한 제품 혹은 시스템 일반적인 계산 목적이 아니라 특별한 임무를 수행하도록 프로그램이 내장되어 있는 시스템 목적에 알맞은 Processor의 특징에 의존한다 일반적으로 보다 큰 시스템의 일부이거나 독립됨 하드웨어와 소프트웨어의 변경이 매우 어려움 가격에 예민함 임베디드 시스템처럼 호스트 시스템과 타겟 시스템이 다를 때 애플리케이션을 개발하기 위해선: 효과적인 개발을 위한 특정 툴과 개발방법이 필요, 개발툴에 Hardware에 대한 Setting을 해줘야 함 Host 시스템이 Target에 알맞은 기계어를 생성하기 위해서 Cross Toolchain이 있어야 한다 타켓 시스템의 디버깅을 위해 전용
소프트웨어 공학
개발
소프트웨어 공학 수업 기말고사 대비 정리입니다. 소프트웨어 공학 공학에는 정해진 기간과 주어진 비용이라는 제한이 있기에, 문제 해결을 위한 기술과 공학적 원리를 활용해야 한다. 그리고 이를 실무에 적용해 문제 해결의 절차를 만들고 반복적인 절차를 개선해 표준을 만들어낸다. 소프트웨어 개발의 어려움을 해결하기 위해 공학을 적용하는 것이 소프트웨어 공학이다. 비용 산정 기법 하향식 전문가 판단 기법 델파이 기법: 전문가의 편견에 영향받지 않도록 조정자를 둠 상향식 코드 라인 수(Line Of Code): 코드 라인 수를 구하고 노력 산정 개발 단계별 노력 기법: 각 단계의 노력 투여를 맨먼스(M/M)로 구함 수학적 COCOMO: 라인 수를 추정하고, 이를 준비된 식에 대입해 M/M 계산 (가
MetalLB
kubernetes
MetalLB는 BareMetal LoadBalancer의 약자로, Kubernetes 클러스터에 연결되어 온프레미스 환경(IDC)에서 로드밸런서 타입 서비스를 구현해주는 툴이다. MetalLB가 제공하는 기능을 크게 나누면 주소를 할당해주는 기능과 외부와 연결하는 기능 두 가지로 나누어 볼 수 있다. 주소 할당 클라우드 제공업체의 Kubernetes 클러스터에서는 로드밸런서를 요청하면 클라우드 플랫폼이 IP 주소를 할당해준다. 베어메탈 클러스터에서는 MetalLB가 이 할당을 담당한다. MetalLB에 사용할 수 있는 IP 주소 풀을 제공하면 해당 풀에서 LB를 생성해준다. 외부 연결 MetalLB가 서비스에 외부 IP 주소를 할당한 후에는 해당 IP가 클러스터에 “존재한다”는 것을 클러스터 외부
시리얼 통신
embedded
병렬통신과 직렬통신 병렬통신(Parallel Communication) 다수의 비트(bit)를 한번에 전송하는 방법이다. 이들은 보통 8 또는 16 또는 그 이상의 라인을 통해 동시에 데이터를 보냄 타이밍(clock)에 맞춰 모든 라인이 같이 동작할 수 있도록 clock(CLK) 라인이 필요하므로 8-bit data bus의 경우 9라인을 사용한다. 패러럴은 빠르고 상대적으로 구현이 쉽지만 input/output(I/O) 라인을 많이 소모한다. 직렬통신(Serial Communication) 데이터를 스트림으로 바꿔서(직렬화, serialization) 한 번에 한 비트씩 전송한다. 시리얼 인터페이스는 clock 라인 포함 2라인으로 데이터를 전송한다. 동기 시리얼과 비동기 시리얼 동기식 시리얼(Sy
가장 가까운 두 점
알고리즘
2차원 평면상에 n개의 점이 주어졌을 때, 이 점들 중 가장 가까운 두 점을 구하는 프로그램을 작성하시오. 점을 x 좌표 기준으로 정렬한 다음, x좌표가 현재까지의 최소 거리 범위 안에 있는 점 중 y좌표도 현재까지의 최소 거리 범위 안에 있는 점들을 순회하며 최소값을 구하면 풀린다. 같은 위치의 점이 여러개 있을 것을 고려해서 multiset을 썼었는데 multiset을 쓰니 시간초과가 났다… 어차피 같은 위치의 점은 정렬 후에도 바로 옆에 붙어있을 것이고, 이 때문에 항상 S라는 set에 이전 점이 남아있는 동안 이후 점과 비교하게 되어 상관없다. include&x3C;iostream>include&x3C;algorithm>incl
담금질 기법
알고리즘
담금질 기법은 기본적으로 문제 공간에서 무작위 방향 중 에너지를 최소화하는 경향으로 상태를 확률적으로 바꾸며 해를 탐색한다. 마치 금속을 담금질하는 것과 비슷한 원리라고 해서 Simulated Annealing(모의 담금질) 이라는 이름이 붙었다. 이를 구현하는 방식은 다양하겠지만, 시뮬레이티드 어닐링은 다음과 같이 행동한다. 현재 상태와 인접한 상태를 하나 구한다. 그 상태로 변할 때 얼마만큼 이득인지/손해인지를 판단한다. 얻을 이득과 손해의 정도에 따라 확률적으로 그 상태로 이동한다. 여기서 인접한 상태란, 현재의 상태를 국소적으로 바꾸어서 만들 수 있는 상태이다. 담금질 알고리즘은 이 과정을 반복함을 통해서 최적해를 향해 나아가고, 와중에 더 나빠지는 해에 대해서도 가끔씩은 탐색을 해보면서 지역 최
볼록 껍질과 회전하는 캘리퍼스
알고리즘
볼록껍질(Convex Hull) 여러 점들이 막 주어져 있을때 모든 점을 포함하는 볼록한 다각형을 의미한다. 볼록 껍질에에서 연속한 세 점을 한 쪽 방향으로 잡으면 모든 결과가 같다는 것을 이용하여, CCW 방식으로 구할 수 있다. 볼록껍질을 구하는 대표적인 알고리즘인 Graham Algorithm은 점들을 정렬하는데에서 시작한다. 볼록껍질에 무조건 들어가는 점 하나를 잡는다. (보통 가장 x좌표가, y좌표가 작은 점) 그 점을 기준으로 기울기 순으로 정렬한다. 같은 기울기면 거리 순으로 정렬. 점들을 그룹에 순서대로 넣는다.  넣으면서 그룹의 제일 최근 3점의 ccw가 옳지 않으면 그 세 점 중 중간 점을 뺀다. 3~4를 반복하면서 1번점까지 돌아온다. 코드로 구현하면 아래처럼 된다. vector&
오일러 경로 테크닉
알고리즘
다음과 같은 트리가 있다고 가정해보자. 1번 정점이 루트이고, DFS 방문 순서대로 번호가 붙여져있다. 이 트리를 배열에 저장하면 각 정점을 루트로 하는 서브트리를 구간으로 나타낼 수 있게 된다. (번호가 DFS 방문 순서대로 되어있어야 성립한다. 일반적인 트리가 주어지는 경우 구간을 계산하기 위한 번호를 다시 붙여야 한다.) 구간의 시작지점은 각 정점이 처음 방문 되었을 때, 끝 지점은 그 정점에서의 DFS함수가 끝났을 때의 번호를 저장함으로써 알 수 있다. 이것을 이용하는 것이 오일러 경로 테크닉이다. 오일러 경로 테크닉을 활용하는 대표적인 문제로 회사 문화 2,3,4가 있다. 회사 문화 2 영선회사에는 상사가 직속 부하를 칭찬하
왜판원순회
알고리즘
외판원 문제는 그래프에서 모든 정점을 방문하여 시작점으로 돌아오는 최단경로를 찾아야 하는 유명한 문제이다. 왜판원 문제의 목표는 조금 다르다. 정점의 개수가 N개인 그래프에서 역시 모든 정점을 방문하여 시작점으로 돌아오되, 정확히 그 길이가 L인 경로가 존재하는지를 알아내야 한다. 다시 말해서, 경로의 길이가 L이고 크기가 N인 싸이클이 존재하는지를 알아내야 한다. Meet in the middle을 활용한 문제이다. 이론상으로는 구상했는데 복잡하게 생각하다보니 로직이 꼬여서 많이 고전했다.. claude와의 진지한 대화로 리팩토링해서 성공했다. 특정 점이 중간에 방문하는 점이라고 가정한다. 시작 점으로부터 해당 점까지 도달하는
직사각형 스위핑
알고리즘
직사각형 합집합 면적 구하기 기본적으로 각 직사각형의 꼭짓점이 되는 점을 x좌표 기준으로 스위핑하면서 각 점 사이의 사각형 넓이를 구하는 식으로 답을 구한다. 위 그림과 같이 두 직사각형이 주어지면, 노랑, 빨강, 파랑에 해당하는 사각형의 넓이를 각각 구한 후 더하는 것이다. 이를 위해서 우선 각 직사각형의 x 시작 좌표, x 끝 좌표와 y 시작 및 끝을 저장해놓는다. 그리고 x를 기준으로 정렬한다. cnt라는 이름의 세그먼트 트리에 y 범위에 대해 x 시작 좌표에서 +1, x 끝 좌표에서 -1을 해준다. cnt가 1 이상이면 (직사각형이 있는 구간이면) tree라는 이름의 세그먼트 트리에 직사각형이 있는 y 구간의 총 높이를 저장한다
Audio Codec
embedded
오디오의 Raw 데이터는 너무 크기 때문에 통신이나 저장시에 효율이 좋지 못함 Audio Codec는 이러한 문제점을 해결하기 위해서 Raw 데이터를 압축할 수 있는 방법을 제시 종류 G.711, G.722, G.723.1, G.729: 통신 프로토콜 표준 단체인 ITU-T에서 표준으로 정의한 코덱으로 통신에 주로 사용 AAC, AC3, MP3, etc..: ISO혹은 민간기업등에서 정의한 압축 알고리즘으로 음악/영화 등에 주로 사용 G.711 음성에 있어서의 ITU 표준/H.323환경에서 음성전달 전송방식의 기본 오디오 코덱 표준안 G.711은 64Kbps에서 3KHz의 전화급 오디오 품질을 제공하기 위하여 PCM 오디오 엔코딩과 미국, 유럽에서 주로 이용하는 U-law 또는 A-law
I2C
embedded
Inter-Integrated Circuit(I2C) 프로토콜은 IC 사이에 통신 링크를 제공하는 양방향 2 와이어 직렬 버스이다. IIC 혹은 TWI(The Two-Wire Serial Interface)라고도 불린다. Philips Semiconductors 에 의해 1980 년대 초기에 개발 초기에는 텔레비전에서 CPU를 주변 칩에 연결할 방법을 제공하기 위해 만들어졌다. 오늘날에는 오디오와 비디오 장비뿐만 아니라 많은 다른 응용 분야에서 사용하며, 사실상의 표준으로서 산업계에서 보편적으로 수용되고 있다. 하나의 마스터와, 다른 하나의 슬레이브로 구성 된다. 그리고 슬레이브는 127개까지 구성이 가능하다. 즉, 메인 ECU가 있으면, 그 외 여러가지 디바이스들이 묶여 통신이 가능하다.
CPU Load Average
kernel
리눅스 커널에서는 CPU Load을 평균으로 산출하여 스케쥴링 알고리즘과 CPU 로드 밸런싱등에 사용한다. 여기서 산출하는 CPU Load 평균은 해당 CPU 실행큐에 대해서 전역적(global)으로 걸리는 부하 평균이다. 이동평균(Moving Average) 리눅스 커널에서는 CPU 부하 평균(Load Average)을 “이동평균” 방식으로 산출한다. 이동평균(Moving Average)은 선택한 범위(날짜 혹은 시간)안에서 발생한 수치들의 평균이다. 예를들어 정리하면 다음과 같다. 1일 이동평균은 1일동안 발생한 수치들의 평균. 5일 이동평균은 5일동안 발생한 수치들의 평균. 15일 이동평균은 15일동안 발생한 수치들의 평균. 1분 이동평균은 1분동안 발생한 수치들의 평균. 5분 이동평균은 5분동안
cgroup
process
cgroup은 Control group의 약자로, 커널에서 프로세스를 계층적 그룹으로 합쳐 관리하기 위한 기능이다. cgroup을 통해 해당 그룹이 사용할 수 있는 CPU, memory를 제한하는 등의 제어를 할 수 있다. cgroup 설정 방법 cgroup는 /sys/fs/cgroup 하위의 파일로 정의된다. cgroup은 오직 프로세스(태스크)들을 그룹화 하는 역할만 하며 내부적으로 자원을 제한하거나 할당하는 역할은 서브시스템에서 수행한다. cgroup 설정을 수정하기 위해선 cgroup 가상파일시스템을 마운트하여 파일 및 디렉토리를 직접 조작하거나, 사용자 도구(Debian, ubuntu는 cgroup-bin/RHEL, CentOS는 libcgroup)를 사용할 수 있다. 서브시스템 서브시스템은 cgr
AWS Organization
aws
AWS Organization는 AWS 계정 (accounts)을 단일 단위로 통합해 관리할 수 있는 개체이다. Organization 안의 모든 계정을 중앙에서 확인하고 관리할 수 있다. AWS Organizations는 비즈니스의 예산, 보안과 규정 준수 필요 충족에 도움이 되는 계정 관리 및 통합 결제 기능까지 함께 제공한다. 조직의 관리자로서 조직에서 계정을 생성하고 기존 계정을 조직에 초대할 수 있다. 1개의 관리자 계정(management account)과 0개 이상의 멤버 계정(member account)을 갖고 있다. 위 그림에 나타나 있듯이 tree 계층 구조로 OU를 생성할 수 있다. 각 계정(Each Account)을 OU에 포함하거나 루트에 포함할 수 있다. 루트 (Root) Orga
테스팅 용어
테스팅
테스팅의 기초 테스팅: 소프트웨어 제품과 관련 작업 산출물이 특정 요구명세를 만족하는지 결정하고, 목적에 부합하는지 입증하고 결함을 찾아내기 위해 해당 산출물을 계획, 준비, 평가하는 정적/동적인 모든 수명주기 활동으로 구성된 프로세스 커버리지: 특정한 커버리지 항목이 테스트 스위트에 의해 이행되는 백분율 정도 디버깅: 소프트웨어에서 장애의 원인을 발견하고, 분석하여 제거하는 절차 테스트 오라클: 테스트 대상 소프트웨어의 실제 결과와 비교할 목적으로 예상 결과를 결정하는 근거   밸리데이션: 요구사항이 컴포넌트나 시스템을 특정하게 의도적으로 사용 또는 활용하는 것을 충족시키는지 조사에 의해서나 객관적인 증거 제공으로 확인하는 것. 베리피케이션: 명세된 요구사항이 충족되었는지를 조사에 의해서나 객관적인 증거
kprobe와 kretprobe
linux
kprobe와 kretprobe는 커널 코드에 동적으로 중단점을 삽입하여 사용자가 정의하는 핸들러 함수가 실행되도록 하는 도구이다. kprobe는 함수 또는 함수에서 특정 오프셋만큼 떨어진 곳에서 핸들러 함수를 실행해주고, kretprobe는 함수가 끝난 후에 핸들러 함수를 실행하게 한다. kprobe의 동작 방식 kprobe는 커널의 중단점을 삽입할 주소 (함수 + 오프셋)에 존재하는 명령어를 복사해둔 뒤 중단점을 삽입하는 명령어로 덮어씌운다 (i386에서는 int3 명령어로 1바이트이다.) 그럼 i386에서는 int3 명령어를 실행하는 순간 breakpoint exception이 발생해서 kprobe 핸들러로 넘어가게 된다. 그렇게 kprobe에 등록된, 중단점 이전에 실행되어야 하는 pre_h
ProxyFactoryBean
aop
스프링은 서비스 추상화를 프록시 기술에도 동일하게 적용한다. 따라서 스프림은 일관된 방법으로 프록시를 만들 수 있게 도와주는 추상 레이어를 제공한다. ProxyFactoryBean은 프록시를 생성해서 빈 오브젝트로 등록하게 해주는 팩토리 빈이다. ProxyFactoryBean은 순수하게 프록시를 생성하는 작업만을 담당하고 프록시를 통해 제공해줄 부가기능은 별도의 빈에 둘 수 있다. ProxyFactoryBean이 생성하는 프록시에서 사용할 부가기능은 MethodInterceptor 인터페이스를 구현해서 만든다. MethodInterceptor는 InvocationHanler와 비슷하지만 한가지 다른점이 있다. InvocationHandler의 invoke() 메소드는 오브젝트에 대한 정보를 제공하지 않는다.
Spring AOP
aop
AOP란 Aspect Oriented Programming의 약자로 관점 지향 프로그래밍이라고 한다. 여기서 Aspect(관점)이란 흩어진 관심사들을 하나로 모듈화 한 것을 의미한다. 객체 지항 프로그래밍(OOP)에서는 주요 관심사에 따라 클래스를 분할한다. 이 클래스들은 보통 SRP(Single Responsibility Principle)에 따라 하나의 책임만을 갖게 설계된다. 하지만 클래스를 설계하다보면 로깅, 보안, 트랜잭션 등 여러 클래스에서 공통적으로 사용하는 부가 기능들이 생긴다. 이들은 주요 비즈니스 로직은 아니지만, 반복적으로 여러 곳에서 쓰이는 데 이를 흩어진 관심사(Cross Cutting Concerns)라고 한다. AOP 없이 흩어진 관심사를 처리하면 다음과 같은 문제가 발생한다.
Spring에서 aspectj weaving사용하기
aop
Spring은 객체지향적으로 AOP 기술을 구현하기 위해 프록시 패턴의 관점을 선택했다. 이러한 패턴의 추상적인 관점을 구체화하기 위해, Java에서 기본적으로 제공해주고 있는 JDK Dynamic Proxy(프록시 패턴의 관점의 구현체)를 기반으로 추상적인 AOP 기술을 객체 모듈화하여 설계하였다. 또한 Spring은 성숙한 AOP 기술을 제공해주기 위해 Spring 2.0 부터 @AspectJ애노테이션 방식을 지원하였고, Aspect를 구현하는데 있어 AspectJ5 라이브러리에 포함된 일부 애노테이션을 사용할 수 있다. AspectJ의 강력한 AOP 기술을 Spring에서 쉽게 구현할 수 있기 때문에 개발자는 비즈니스 개발에 보다 집중할 수 있다. 물론, @AspectJ 애노테이션 방식을 통해 구현된
트랜잭션 전파
트랜잭션
트랜잭션 전파란 트랜잭션 경계에서 이미 진행 중인 트랜잭션이 있을 때 또는 없을 때 어떻게 동작할 것인가를 결정하는 방식을 말한다. 1. PROPAGATION_REQUIRED 가장 많이 사용되는 트랜잭션 속성이다. 진행 중인 트랜잭션이 없으면 새로 시작하고, 이미 시작된 트랜잭션이 있으면 이에 참여한다. DefaultTransactionDefinition의 트랜잭션 전파 속성은 바로 이 PROPAGATION_REQUIRED이다. 2. PROPAGATION_REQUIRED_NEW 항상 새로운 트랜잭션을 시작한다. 즉. 앞에서 시작된 트랜잭션이 있든 없든 상관없이 새로운 트랜잭션을 만들어서 독자적으로 동작하게 한다. 3. PROPAGATION_NOT_SUPPORTED 트랜잭션이 없이 동작하도록 만들
AOT
spring
Spring AOT 엔진은 빌드 시 스프링 애플리케이션을 분석하고 최적화하는 도구이다. 또한 AOT 엔진은 GraalVM Native Configuration이 필요로 하는 reflection configuration을 생성해준다. 이것은 Spring native 실행 파일로 컴파일 하는데 사용되고 이후에 애플리케이션의 시작 시간과 메모리 사용량을 줄일 수 있게 한다. 그러한 변환은 Maven과 Gradle 스프링 AOT 플러그인에 의해 수행된다. AOT 엔진은 최적화된 애플리케이션 컨텍스트와 애플리케이션을 위해 특별히 제작된 스프링 팩토리(Spring Boot 뒤의 플러그인 시스템)를 생성하기 위해 빌드 시 조건을 평가한다. 이를 통해 아래와 같은 효과를 볼 수 있다. 런타임시 필요한 스프링 인프라가
@TransactionalEventListener
event
Event를 사용할 때 기본적으로 사용하는 @EventListener는 event를 publishing 하는 코드 시점에 바로 publishing*한다. 하지만 우리가 퍼블리싱하는 event는 대부분 메인 작업이 아닌 서브의 작업이 많고 비동기로 진행해도 되는 경우도 많다. 다른 도메인 로직인 경우도 있다. 이럴 경우 조금 애매해지기도 한다. 아래 예를 보자. 아래코드는 @Transactional로 메서드가 하나의 트랜잭션으로 묶여있다. 이 메서드를 실행했을때, 1번과 2번이 정상적으로 마무리되고 3번이 발생하는 도중에 예외처리가 발생하면 어떻게 될까? 3번이 실패했으면 같은 트랜잭션으로 묶여있는 1번도 함께 롤백될 것이다. 하지만 2번은 발행된 이벤트를 listen하는 별도의 구현체가 이후의 동작을 수
Cascade
jpa
cascade 옵션은 jpa를 사용할때 @OneToMany나 @ManyToOne에 옵션으로 줄 수 있는 값이다. cacade 옵션을 사용하면 부모 엔티티에 상태 변화가 생길 때 그 엔티티와 연관되어있는 엔티티에도 상태 변화를 전이시킬 수 있다. 즉, 자식 엔티티의 생명주기를 관리할 수 있다. cascade 타입의 종류 PERSIST 부모 엔티티를 저장하면 자식 엔티티까지 함께 저장한다. 다시말해, 명시적으로 부모엔티티와 연관관계를 가진 자식 엔티티 영속화시킬때 따로 명시할 필요 없이 부모.자식 = 자식 인스턴스 과 같이 적으면 자식 엔티티도 데이터베이스에 자동으로 저장된다. MERGE 데이터베이스에서 가져온 부모 객체를 통해 자식 엔티티의 정보를 수정하여 병합했을때 변경 결과가 자식 엔티티에 반
GenerateValue Column에 값을 넣는다면
jpa
Hexagonal architecture를 사용해서 구현하다 문제가 생겼다. 해당 프로젝트에선 기본 PK로 UUID를 사용했고, 새로 생성한 도메인 모델은 id 값을 UUID(0, 0)으로 설정해서 사용했다. (여기서 중요하진 않지만 생성 전략은 IdentifierGenerator로 TimeBasedUUID를 생성할 수 있도록 직접 정의된 상태였다.) UUID(0, 0)으로 설정해주다 보니 기존에는 새 insert문을 날려야하는 경우 isNew가 Persistable 기본 전략에 따라 false로 들어갔고, merge가 호출되었다. 여기에서 알아봤던 것 처럼 영속성 컨텍스트에 등록되지 않은 객체에 대해 merge를 호출하면, 어떤 update문(혹은 insert문)을 날려야하는지를 알아야 하기 때문에 sel
Hibernate dialect
jpa
하이버네이트가 데이터베이스와 통신을 하기 위해 사용하는 언어를 Dialect라고 한다. 모든 데이터베이스에는 각자의 고유한 SQL언어가 있는데, 관계형 데이터베이스끼리 형태나 문법이 어느정도 비슷하긴 하지만, 완전히 똑같지는 않다. 예를 들어 Oracle 쿼리 구문과 MySQL 쿼리구문은 다르다. 하지만, 하이버네이트는 한 데이터베이스관리시스템(DBMS)에 국한되지않고, 다양한 DBMS에 사용 가능하다. 즉 내부적으로 각자 다른 방법으로 처리하고 있는 것이다. 그렇기 때문에특정 벤더(DBMS)에 종속적이지 않고, 얼마든지 대체가능하다. JPA에서는 아래와 같이 Dialect라는 추상화된 언어 클래스를 제공하고 각 벤더에 맞는 구현체를 제공하고 있다. spring: datasource:
JDBC Object Mapping Fundamentalsentity
jpa
스프링 데이터가 객체를 매핑할 떄 담당하는 핵심 역할은 도메인 객체 인스턴스를 생성하고, 여기에 저장소 네이티브 데이터 구조를 매핑하는 일이다. 여기에는 두 가지의 핵심적인 단계가 있다. 노출된 생성자중 하나로 인스턴스 생성하기. 나머지 프로퍼티 채우기. 엔티티(Entity) 생성 Spring Data JDBC에서 엔티티 객체를 생성하는 알고리즘은 3가지이다. 기본 생성자가 있는 경우 기본생성자를 사용한다. 다른 생성자가 존재해도 무시하고 우선적으로 기본생성자를 사용한다. 매개변수가 존재하는 생성자가 하나만 존재한다면 해당 생성자를 사용한다. 매개변수가 존재하는 생성자가 여러개 있으면 @PersistenceConstructor 어노테이션이 적용된 생성자를 사용한다. 만약 @PersistenceCons
FetchJoin
jpql
fetch join은 JPQL에서 성능 최적화를 위해 제공하는 기능이다. 페치 조인은 연관된 엔티티나 컬렉션을 한 번에 같이 조회해준다. 일반적으로 연관관계가 맺어진 엔티티를 조회할때, N+1문제를 해결하기 위해서 FetchType.LAZY를 사용하는 경우가 있다. 하지만 두 엔티티를 모두 조회해야하는 경우엔 두개의 쿼리를 날려야하기 때문에 N+1문제가 동일하게 발생한다. 이럴 때 fetch join을 사용하면 하나의 쿼리로 두 엔티티를 한 번에 조회할 수 있다. 1:N 조인에서 fetch join을 사용하면 결과의 갯수가 늘어날 수 있다.(‘1’쪽에서 조회해야하는 엔티티의 총 갯수가 아닌, ‘1’쪽의 엔티티 갯수만큼의 결과가 조회된다.) 이 경우 JPQL의 DISTINCT를 사용해서 결과의 갯수를 줄일
경로표현식
jpql
자바에서 인스턴스화된 객체로 클래스의 변수나 메서드에 접근할 때 .을 이용해 접근하는 것 처럼, jpql 쿼리에서 .으로 객체의 값에 점을 찍어 객체 그래프를 탐색하는 것을 경로 표현식이라고 한다. 경로 유형별 동작 상태 필드(State Field) 상태 필드는 일반적인 값을 저장하기 위한 필드이다. 즉, int, varchar등의 자료형을 가지는 기본적인 데이터를 저장한다. 상태필드는 더 나아갈 경로가 존재하지 않으므로 jpql에서 부가적인 조인 등의 탐색 또한 일어나지 않는다. 연관 필드(Association field) 연관 필드는 연관관계가 맺어진 외래 테이블의 값을 위한 필드이다. 단일 값 연관 필드와 컬렉션 값 연관 필드로 나뉜다. 단일 값 연관 필드 @ManyToOne, @OneToOne
OrphanRemoval
jpa
cascade 옵션을 사용하면 부모 엔티티에 상태 변화가 생길 때 그 엔티티와 연관되어있는 엔티티에도 상태 변화를 전이시킬 수 있다. 그러나 cascade 옵션을 사용한다고 해서 부모 엔티티에서 자식 엔티티의 생명주기를 완전히 통제할 수 있는 것은 아니다. cascade의 REMOVE 옵션은, 부모 엔티티를 삭제했을때 그 엔티티를 참조하고 있는 자식 엔티티(해당 부모 엔티티를 Foreign Key로 가지고있는 엔티티)도 함께 삭제해준다. 하지만 부모 엔티티에서 자식 엔티티를 삭제했을때에는 그 참조를 끊어줄 뿐, 그 자식 엔티티를 같이 삭제해주진 않는다. (심지어 FK에 NotNull 제약조건을 걸어놨으면 아무 변화도 생기지 않는다) 그럴 때 사용할 수 있는 것이 OrphanRemoval이다
Paging
querydsljpa
Querydsl에서 페이징하는 방법을 알아보자. Page는 인터페이스이기 떄문에, Page를 반환하기 위해선 Page를 구현한 구체클래스를 생성해야한다. 그렇기 때문에 아래 코드에선 스프링 데이터에 있는 PageImpl 클래스를 사용하여 return 하도록 한다. fetchResults()를 사용하여 total count쿼리와 결과 리스트를 한 코드로 조회하도록 할 수도 있지만, fetchResults()와 fetchCount()가 특정 상황에서 제대로 동작하지 않는 이슈때문에 depercated 되었으므로 따로 count를 조회하여 반환하는 방식을 택했다. 원하는 컬럼을 Dto로 만들어서 조건에 따라 조회한 후 반환하는 예제 코드이다. public Page&x3C;MemberTeamDto> sear
QuerydslJpa와 QClass
querydsljpa
Spring Data JPA가 기본적으로 제공해주는 CRUD 메서드 및 쿼리 메서드 기능을 사용하더라도 원하는 조건의 데이터를 수집하기 위해선 JPQL을 작성해야한다.JPQL로 간단한 로직을 작성하는데는 큰 문제가 없지만, 복잡한 로직의 경우 쿼리 문자열이 상당히 길어진다. 또, 정적 쿼리인 경우엔 어플리케이션 로딩 시점에 JPQL 문자열의 오타나 문법적인 오류를 발견할 수 있지만, 그 외는 런타임 시점에서 에러가 발생한다는 문제가 있다. 이러한 문제를 해결하기 위한 프레임워크가 바로 QueryDSL-jpa이다. QueryDSL을 사용하면 문자가 아닌 코드로 쿼리를 작성할 수 있기 때문에 컴파일 시점에 문법 오류를 쉽게 확인할 수 있고, 타입 안정성(type-safe)을 지키면서 동적인 쿼리를 편리하게
ReadOnlyQuery 최적화
jpa
JPA의 영속성 컨텍스트는 변경 감지를 위해 스냅샷 인스턴스를 보관하는 특징이 있다. 하지만 엔티티를 단순 조회하는 경우에는 컨텍스트에 있는 엔티티를 다시 꺼내오거나 수정할 필요가 없기 때문에 스냅샷 인스턴스를 저장하는 것이 메모리적으로 낭비이다. 이럴 경우 아래의 방법으로 메모리 사용량을 최적화할 수 있다. 스칼라 타입으로 조회 스칼라 타입은 영속성 컨텍스트가 관리하지 않기 떄문에, 엔티티가 아닌 스칼라 타입으로 조회하면 읽기 전용 쿼리에서 메모리를 절약할 수 있다. SELECT u.id, u.name, u.age FROM user u 읽기 전용 쿼리 힌트 사용 하이버네이트 전용 힌트인 org.hibernate.readOnly를 사용하면 엔티티를 읽기 전용으로 조회할 수 있다. 읽기 전용이므로
1차캐시
캐싱
캐시란 무엇일까? Cache는 간단히 말해서 나중의 요청에 대한 결과를 미리 저장했다가 빠르게 사용하는 것이다. 컴퓨터에서 중요한 메인 데이터들은 전원이 꺼져도 저장되는 SSD, HDD 등의 Secondary Memory에 저장된다. Secondary Memory에 저장된 데이터들은 장기적으로 안정적이게 저장될 수 있지만, 기술 한계상 데이터를 IO 하는 속도가 느리다. 그렇기 때문에 컴퓨터에서는 데이터 처리에 바로 필요한 데이터를 Main Memory인 RAM에 끌어놓거나, CPU에서 빠르게 접근할 수 있는 CPU Registers, Cache Memory의 형태로 저장하여 더 빠르고 쉽게 접근할 수 있도록 한다. 애플리케이션 서버(Spring JPA?)가 DB에 접근할 때를 예로 들어보면, DB에 연결
2차캐시
캐싱
애플리케이션에서 공유하는 캐시를 JPA는 공유 캐시(Shared Cache)또는 2차 캐시 (Second Level Cache, L2 Cache)라 부른다. 분산 캐시나 클러스터링 환경의 캐시는 애플리케이션보다 더 오래 유지 될 수도 있다. 2차 캐시를 적절히 활용하면 데이터베이스 조회 횟수를 획기적으로 줄일 수 있다. 1차캐시는 못하고 2차캐시는 할 수 있는 것 1차캐시는 영속성 컨텍스트에서 관리되는 캐시로, 트랜잭션이 시작하고 종료할 때 까지만 유지된다. 그렇기 때문에 같은 트랜잭션에서 한 엔티티를 여러번 가져와야할때 효과를 볼 수 있다. 하지만 만약에 여러 유저가 한 엔티티의 정보를 필요로 한다면 어떨까? 여러 요청들에서 공통적으로 같은 엔티티의 데이터가 필요한 경우에는, 1차캐시가 효용을 미치지 못한
영속성 컨텍스트
캐싱
영속성 컨텍스트랑 말 그대로 엔티티를 영속화(영구저장) 시켜주는 환경이다. 애플리케이션과 데이터베이스 사이에서 객체를 보관하는 가상의 데이터베이스(1차캐시) 역할을 한다. 엔티티 매니저를 통해 엔티티를 저장하거나 조회하면 엔티티 매니저는 영속성 컨텍스트에 엔티티를 보관하고 관리한다. 영속성 컨텍스트는 엔티티 매니저를 생성할 때 하나 만들어지고, 엔티티 매니저를 통해 영속성 컨텍스트에 접근하고 관리할 수 있다. 영속성 컨텍스트는 엔티티를 여러가지 상태로 저장한다. 엔티티의 생명주기 비영속(new/transient): 영속성 컨텍스트와 전혀 관계가 없는 상태 영속(managed): 영속성 컨텍스트에 저장된 상태 준영속(detached): 영속성 컨텍스트에 저장되었다가 분리된 상태 삭제(removed): 삭제
트랜잭션 전파 설정
jpa
Spring에서 사용하는 어노테이션 @Transactional은 해당 메서드를 하나의 트랜잭션 안에서 진행할 수 있도록 만들어주는 역할을 한다. 이때 트랜잭션 내부에서 트랜잭션을 또 호출한다면 스프링에서는 어떻게 처리하고 있을까? 새로운 트랜잭션이 생성될 수도 있고, 이미 트랜잭션이 있다면 부모 트랜잭션에 합류할 수도 있을 것이다. 진행되고 있는 트랜잭션에서 다른 트랜잭션이 호출될 때 어떻게 처리할지 정하는 것을 ‘트랜잭션의 전파 설정’이라고 부른다. 전파 설정 옵션 트랜잭션의 전파 설정은 @Transactional의 옵션 propagation을 통해 설정할 수 있다. 각 옵션은 아래와 같다. REQUIRED (default) 부모 트랜잭션이 존재한다면 부모 트랜잭션으로 합류하고, 부모 트랜잭션이 없다면 새
CSRF
springsecurity
CSRF(Cross site Request forgery)는 웹 애플리케이션의 취약점 중 하나로, 이용자가 의도하지 않은 요청을 통한 공격을 의미한다. 즉, 인터넷 사용자가 자신의 의지와 무관하게 공격자가 의도한 특정 행위를 웹사이트의 요청하도록 하여 간접적으로 해킹하도록 하는 것이다. 따라서, 스프링 시큐리티는 CSRF 공격을 방지하기 위한 기능을 가지고있다. @EnableWebSecurity 어노테이션을 붙이면 Referrer 검증, CSRF Token 사용 등의 기능이 활성화된다. 각 기능에 대해 간단하게 알아보자 Referrer 검증 서버단에서 request의 referrer을 확인하여 domain이 일치하는지 검증하는 방법이다. Spring Security CSRF Token 임의의 토큰을
@GroupSequence
validation
보통 WebRequest를 받을때, null이거나 비어있는 등의 유효하지 않은 값을 미리 걸러내기 위해 Sprign validation을 사용한다. 설정해둔 @NotNull, @Size, @Pattern 등 조건에 부합하지 못하면 MethodArgumentNotValidException이 발생하고, 이 에러를 적절히 처리하여 반환하는 방식이 많이 사용된다. 하지만 한 필드에 여러 검증을 넣게 되면, 그 검증에 순서가 부여되지 않아 무작위로 먼저 걸리는 조건의 에러가 반환된다. 그렇다면 이 에러 처리의 순서를 정해줘야 한다면 어떻게 해야할까? 즉, Null 체크를 먼저하고, 그다음 Size를 체크하고, 그다음 Pattern을 체크하는 방식으로 흐름을 지정하려면 어떻게 해야할까? 그런 경우 @GroupSeque
Request 처리과정
web mvc
Spring Web MVC 에서 HTTP Request를 처리하는 핵심 클래스는 DispatcherServlet이란 클래스이다. 아 DispatcherServlet은 MVC 아키텍처로 구성된 프레젠테이션 계층을 만들 수 있도록 설계되어 있다. 서버가 브라우저 등의 HTTP 클라이언트로부터 요청을 받아 처리 후 응답하기까지의 과정을 알아보자. 1. DispatcherServlet의 요청 접수 자바 서버의 서블릿 컨테이너는 HTTP 프로토콜을 통해 들어오는 요청을 DispatcherServlet에 전달해준다. (이때, URL이나 확장자를 설정해주면 일부 요펑만 매핑되도록 설정할 수도 있다.) DispatcherServlet은 요청을 제일 먼저 받아 원하는 전처리 동작을 수행한 후 다음 클래스에게 일부
R2DBC
r2dbc
R2DBC는 Reactive Relational Database Connectivity의 줄임말이다. R2DBC는 관계형 데이터베이스 접근을 위해 구현해야 할 리액티브 API를 선언하는 스펙이다. JDBC는 완전한 블로킹 API이었고, RDBMS는 NoSQL에 비해 자체 리액티브 클라이언트를 가지고 있는 경우가 적어서 비동기 통신을 하기 힘들었다. 반면에 R2DBC는 Non-Blocking 관계형 데이터베이스 드라이버와 잘 동작하도록 하는 것을 목적으로 만들어졌다. 쿼리를 소켓에 기록하고 스레드는 응답이 수신될 때까지 다른 작업을 계속 처리하여 리소스 오버헤드를 줄이는 방식으로 적은 스레드, 하드웨어 리소스로 동시 처리를 제어할 수 있도록 한다. 하지만, R2DBC는 개념적으로 쉬운 것을 목표로 하므로, 기
Ioc와 DI
기본원리
🍃 제어의 역전 IoC (Inversion of Control) 기존에는 클라이언트 구현 객체가 스스로 필요한 서버 구현 객체를 생성하고, 연결하고, 실행하는 프로그램. 즉, 구현 객체가 프로그램의 제어 흐름을 조정하는 프로그램이 많았다. 하지만 이런 방식은 코드의 재사용성과 유지보수성이 낮다. 하지만 그와 반대로 프로그램에 대한 제어 권한을 외부에서 가지고 있는 것을 제어의 역전(Ioc)이라고 한다. IoC는 객체지향성을 잃지 않고 유지보수성이 높은 코드를 만들 수 있게 해준다. (+ 프레임워크는 작성된 코드를 제어하고 대신 실행해주는 역할을 한다. Spring도 이와 같은 프레임워크의 일종이다.) IoC의 장점 애플리케이션 코드의 양을 줄일 수 있다. 클래스 간의 결합을 느슨하게 한다. 애플리케이
Reflection과 직렬화
기본원리
Reflection은 런타임에 동적으로 클래스들의 정보를 알아내고, 실행할 수 있는 것을 말한다. Reflection은 프로그래머가 데이터를 보여주고, 다른 포맷의 데이터를 처리하고, 통신을 위해 serialization(직렬화)을 수행하고, bundling을 하기 위해 일반 소프트웨어 라이브러리를 만들도록 도와준다. java와 같은 객체지향 프로그래밍언어에서 Reflection을 사용하면 컴파일 타임에 인터페이스, 필드, 메소드의 이름을 알지 못해도 실행중에 접글할 수 있다. 또, 멤버 접근 가능성 규칙을 무시하여 private 필드의 값을 변경할 수 있다. 직렬화 jackson은 java.lang reflection 라이브러리를 사용한다. 기본생성자가 있는 경우에는 _constructor.newInsta
기본원리
스프링 컨테이너(Spring Container) 스프링에서 DI를 이용하여 애플리케이션을 구성하는 여러 빈(Bean)들의 생명주기(Lifecycle)와 애플리케이션의 서비스 실행 등을 관리하며 생성된 인스턴스들에게 기능을 제공하는 것을 부르는 말이다. 프로그래머의 개입 없이도 컨테이너에 설정된 내용에 따라 빈을 알아서 참조하고 관리한다. 대표적으론 BeanFactory와 ApplicationContext 가 있다. BeanFactory 스프링 컨테이너의 최상위 인터페이스로서, 스프링 빈을 관리하고 조회하는 역할을 담당힌디. getBean() 을 제공한다. 지금까지 우리가 사용했던 대부분의 기능은 BeanFactory가 제공하는 기능이다. ApplicationContext BeanFactory 기능을 모두 상
선점 잠금과 비선점 잠금
기본원리
운영자 스레드와 고객 스레드는 같은 주문 애그리거트를 나타내는 다른 객체를 구하게 된다. 운영자 스레드와 고객 스레드는 개념적으로 동일한 애그리거트이지만 물리적으로 서로 다른 애그리거트 객체를 사용한다. 위 그림과 같은 상황에서 두 스레드는 각각 트랜잭션을 커밋할 때 수정한 내용을 DB에 반영하는데, 상태가 서로 충돌되기 때문에 애그리거트의 일관성이 깨진다. 이 순서의 문제점은 운영자는 기존 배송지 정보를 이용해서 배송 상태로 변경했는데 그 사이 고객은 배송지 정보를 변경했다는 점이다. 즉 애그리거트의 일관성이 깨지는 것이다. 이런 문제가 발생하지 않도록 하려면 다음 두 가지 중 하나를 해야한다. 운영자 배송지 정보를 조회하고 상태를 변경하는 동안 고객이 애그리거트를 수정하지 못하게 막는다. 운영자가 배
싱글톤
기본원리
웹 애플리케이션은 보통 여러 고객이 요청을 동시에 보내는데, 이럴 때 마다 새로운 객체를 생성해서 반환하는 것은 메모리 낭비가 너무 심하다. 그래서 고안된 것이 생성된 하나의 객체를 공유해서 사용하도록 설계한 ‘싱글톤 패턴’이다. 싱글톤 패턴은 이미 만들어진 객체를 재사용하기 때문에 객체를 생성하는 데 메모리와 시간을 쓰지 않아도 되니 아주 효율적이다! 하지만 싱글톤 패턴도 단점이 있다. 싱글톤 패턴의 문제점 싱글톤 패턴을 구현하는 코드 자체가 많이 들어간다. 의존관계상 클라이언트가 구체 클래스에 의존한다. DIP를 위반한다. 클라이언트가 구체 클래스에 의존해서 OCP 원칙을 위반할 가능성이 높다. 테스트하기 어렵다. 내부 속성을 변경하거나 초기화 하기 어렵다. private 생성자로 자식 클래스를 만들기
웹서버와 WAS
was
웹 서버(Web Server) 웹 서버란 HTTP 프로토콜을 기반으로 클라이언트가 웹 브라우저에서 어떠한 요청을 하면 그 요청을 받아 정적 컨텐츠를 제공하는 서버이다. 정적 컨텐츠란 단순 HTML 문서, CSS, 이미지, 파일 등 즉시 응답 가능한 컨텐츠이다. 이때 웹 서버가 정적 컨텐츠가 아닌 동적 컨텐츠를 요청받으면 WAS에게 해당 요청을 넘겨주고, WAS에서 처리한 결과를 클라이언트에게 전달하는 역할도 해준다. 이러한 웹 서버에는 Apache, NginX등이 있다. WAS(Web Application Server) WAS란 DB 조회 혹은 다양한 로직 처리를 요구하는 동적 컨텐츠를 제공하기 위해 만들어진 Application 서버이다. HTTP 프로토콜을 기반으로 사용자 컴퓨터나 장치에 애플리케이션을
netty의 thread 모델
netty
이벤트 루프란 이벤트를 실행하기 위한 무한루프 스레드를 말한다. 위의 그림과 같이 객체에서 발생한 이벤트는 이벤트 큐에 입력되고 이벤트 루프는 이벤트 큐에 입력된 이벤트가 있을 때 해당 이벤트를 꺼내서 이벤트를 실행한다. 이것이 이벤트 루프의 기본 개념이다. 이벤트 루프는 지원하는 스레드 종류에 따라서 단일 스레드 이벤트 루프와 다중 스레드 이벤트 루프로 나뉜다. 이것을 reactor pattern이라 부르기도 한다. single thread event loop 현재는 다중 코어나 CPU를 장착한 시스템이 일반적이므로 최신 애플리케이션은 시스템 리소스를 효율적으로 활용하기 위해 정교한 멀티스레딩 기법을 이용하는 경우가 많다. 자바 초창기의 멀티스레딩 체계는 동시 작업 단위를 실행하기 위해 필요할 때마다 새
webFlux와 netty
netty
Spring MVC는 기본적으로 블럭킹이고 동기방식을 사용한다. 비동기 처리 기능이 스프링 프레임워크 3에서 추가되어 지원된다고 하지만, 서블릿은 응답을 기다리는 동안 pool의 스레드들은 여전히 지연시킬 수 있기 때문에 전체 stack이 reactive 해야 하는 요구를 충족시킬 수 없다. 이러한 요구사항에 맞추어 스프링 프레임워크5에 도입된 대안적인 모듈이 바로 WebFlux이고, 웹 요청을 reactive 하게 다루는 데에 초점이 맞추어져 있다. 기존의 서블릿 기반의 Spring Boot는 Tomcat을 기반으로 동작한다. 반면 Spring Boot WebFlux는 여러 가지를 고를 수 있는데, Default로 Netty를 사용한다. Netty를 사용하는 이유는 tomcat은 요청 당 하나의 스레드가
Pyroscope Distributor and Ingester
grafana
Distributor Distributor는 Agent로부터 프로파일링 데이터를 받아 처리하는 Stateless 컴포넌트이다. Distributor는 데이터를 일괄 처리하여 여러 Ingesters에 병렬로 보내고, 시리즈를 Ingesters 사이에 나누며, 각 시리즈를 구성된 복제 요소에 따라 복제한다. 기본적으로 구성된 복제 요소는 세 개이다. 유효성 검사 Distributor는 데이터를 Ingester에 전달하기 전에 유효성을 검사, 변환 절차를 거친다. 데이터 중 일부 샘플만 유효하다면 유효한 데이터만 Ingester에 전달하고, 유효하지 않은 데이터는 Ingesters에 보내지지 않는다. 요청에 유효하지 않은 데이터가 포함되어 있으면 Distributor는 Bad Request 코
AWS 2024 Summit Seoul
aws
2024/05/16(목) AWS Summit 데이터 처리도 이제는 컨테이너로, 우아한 형제들의 데이터 플랫폼 혁신 컨테이너로 데이터 처리하기 데이터 처리의 어려움 인프라 구성 다양한 데이터 포맷, 프레임워크 급격한 데이터량 증가 빠르게 변화하는 비즈니스 컨테이너와 데이터 처리를 결합한다면? 이미지 기반으로 쉽게 패키징할 수 있음 컴퓨팅 작업을 빠르고 유연하게 확보할 수 있음 대표적인 방법: EMR on EKS 특징 하나의 EMR 워크로드를 다수의 Pod로 구성 EKS 워크로드에 필요한 코드, 라이브러리, 프레임워크를 컨테이너 이미지에 내장 EMRFS/S3를 데이터 저장소로 활용 Spark, Flink 지원 장점 빠르고 유연한 컴퓨팅 자원 활용 (Karpenter 활용) 하나의 EK
Platform Engineering
devops
플랫폼 엔지니어링은 클라우드 네이티브 시대에 소프트웨어 엔지니어링 조직의 작업을 촉진하고 가속화하기 위한 플랫폼을 설계하고 제공하는 분야이다. 다시 말해, 플랫폼 엔지니어링의 목적은 “소프트웨어 엔지니어링 조직이 일을 더 빠르게 잘 할 수 있도록 하는 것”이고, 그 문제를 “플랫폼”을 통해 해결한다. 애플리케이션을 빠르게 제공할 수 있도록 지원하는 DevOps와도 비슷한 목적을 가지고 있다. 개발과 운영 조직의 비효율성을 문화와 도구들을 이용해 해결하려는게 DevOps라면, 플랫폼 엔지니어링은 DevOps의 도구로 ‘플랫폼’을 채택한 것이라는 차이가 있다. 플랫폼 엔지니어링 팀은 DevOps 방법론 위에서 소프트웨어 엔지니어링 팀, 프로덕트 팀을 지원할 수 있는 플랫폼을 만든다. 플랫폼 엔지니어링은 아래와
Docker와 PID1
container
1. 배경 Linux 신호는 컨테이너 내부의 프로세스 수명 주기를 제어하는 주요 방법이다. 앱의 수명 주기를 앱이 포함된 컨테이너와 긴밀하게 연결하려면 앱이 Linux 신호를 올바르게 처리하도록 해야한다. 프로세스 식별자(PID)는 Linux커널이 각 프로세스에 제공하는 고유한 식별자이다. PID는 namespace다. 즉, 컨테이너에는 호스트 시스템의 PID가 매핑되는 고유한 PID 세트가 있다. Linux 커널을 시작할 때 실행된 첫 번째 프로세스에는 PID 1이 있다. 정상적인 운영체제의 경우 이 프로세스는 init 시스템(ex. systemd 또는 SysV)이다. 마찬가지로 컨테이너에서 실행된 첫 번째 프로세스는 PID 1을 얻는다. Docker와 Kubernetes는 신호를 사용하여
메모리 로딩
bpf
BPF는 일반적인 프로그램과 유사한 방식으로 개발하기 때문에 유사한 실행파일 및 메모리 구조를 가지고 있지만, 커널 안에서 제한된 환경으로 실행되기 때문에 로딩(loading) 또한 다른 방식으로 실행된다 데이터 유형 일반적인 실행파일에서 가장 중요한 두 가지는 코드와 데이터이다. 코드는 말그대로 상위언어를 컴파일한 머신코드를 의미하고, 데이터는 실행시 코드가 참조하는 메모리를 의미한다. 데이터는 스택과 힙같이 실행시 메모리가 할당/해제되는 동적 데이터와 전역변수처럼 코드에서 선언되는 정적 데이터로 나뉘는데, 정적 데이터는 실행파일을 로딩할 때 메모리가 할당되고 해당 메모리를 참조하는 코드도 재배치(relocation)된다. 그리고 정적 데이터는 크게 읽기전용 변수, 초기화된 전역변수 그리고
서브프로그램
bpf
BPF는 일반적으로 하나의 함수(main 함수)가 하나의 섹션이 되고, 하나의 섹션이 하나의 프로그램이 된다. 그리고 커널에서 해당 프로그램을 실행할 때는 프로그램의 시작 위치가 메인함수의 시작 위치이기 때문에 간단히 처음부터 실행하면 된다. 하지만 아래와 같이 메인함수에서 공통함수를 호출하는 경우처럼 두 개 이상의 함수가 필요한 경우에는 프로그램의 시작 위치를 어떻게 보장할까? BPF는 이러한 상황에서 시작 위치 보장을 위해 서브프로그램이라는 기능을 제공한다. 아래 코드는 bcc의 filetop 예제코드이다. 해당 예제는 vfs_read와 vfs_write 커널함수에서 각각 사용할 두 개의 BPF 메인함수와 두 개의 함수에서 사용하는 공통함수(probe_entry)로 구성되어 있다. static
vim 단축키
vi
Vim 이동 기본 이동 -h, j, k, l : 좌, 하, 상, 우 커서 이동 - : 줄의 처음 위치로 커서 이동 gg : 맨 위로 커서 이동 shift + g : 맨 아래로 커서 이동 단어 단위로 이동 w : 단어의 시작 위치로 커서 이동 (오른쪽 방향) b : 단어의 시작 위치로 커서 이동 (왼쪽 방향) e : 단어의 마지막 위치로 커서 이동 (오른쪽 방향) ge : 단어의 마지막 위치로 커서 이동 (왼쪽 방향) 한 문장 내에서 이동 0 (숫자) : 라인 맨 앞으로 커서 이동 ^ : 문장 맨 앞으로 커서 이동 $ : 문장 맨 뒤로 커서 이동 현재 페이지에서의 이동 shift + h : 현재 보이는 페이지에서 커서를 맨 위로 이동 shift + m : 현재 보이는 페이지에서 커서를 중간 위치로
가상스레드
thread
2023년 9월 19일에 릴리즈된 Java 21에서 ‘가상 스레드’ 라는 기능이 추가되었다. 가상 스레드란 기존의 전통적인 Java 스레드보다 가벼운 경량 스레드이다. 자바의 전통적인 스레드는 OS 스레드를 랩핑(wrapping)한 것으로, 플랫폼 스레드라고도 부르는데, 경량 스레드는 OS 스레드를 그대로 사용하지 않고 JVM 자체적으로 내부 스케줄링을 통해서 사용할 수 있도록 한다.는 낭비를 줄여야 할 필요가 있었다. 이 때문에 Non-blocknig 방식의 Reactive Programming이 발전하였다. 비동기 방식의 Reactive 프로그래밍을 사용하면 낭비되었던 스레드를 다른 요청을 처리하는데 사용할 수 있다. 하지만 이런 Reactive 코드는 이해하기 어렵고, 다른 라이브러리를 모두
epoll
system call
Epoll은 리눅스에서 select의 단점을 보완하여 사용할 수 있도록 만든 I/O 통지 모델이다. 파일 디스크립터를 커널이 관리하기 때문에 CPU는 계속해서 파일 디스크립터의 상태 변화를 감시할 필요가 없고, 관찰대상의 정보를 매번 전달하지 않아도 된다. select는 어느 파일 디스크립터에 이벤트가 발생하였는지 찾기 위해 전체 파일 디스크립터에 대해서 순차검색을 위한 FD_ISSET 루프를 돌려야 하지만, Epoll는 이벤트가 발생한 파일 디스크립터들만 구조체 배열을 통해 넘겨주므로 메모리 카피에 대한 비용이 줄어든다. level vs edge trigger epoll의 이벤트 탐지 방법은 level-trigger와 edge-trigger 두 가지가 있다. level-trigger: 특정한 조건이 유
동시성
스레드
대부분의 요즘 운영 체제에서, 실행되는 프로그램의 코드는 프로세스 내에서 실행되고, 프로그램 내에서도 동시에 실행되는 독립적인 스레드를 가진다. 계산 부분을 여러 개의 스레드로 쪼개는 것은 프로그램이 동시에 여러 개의 일을 할 수 있기 때문에 성능을 향상시킬 수 있지만, 프로그램을 복잡하게 만들기도 한다. 러스트 표준 라이브러리는 언어 런타임의 크기를 작게 유지하기 위해 1:1 스레드 구현만 제공한다. 스레드 생성 새로운 스레드를 생성하기 위해서는 thread::spawn 함수를 호출하고, 새로운 스레드 내에서 실행하기를 원하는 코드가 담겨 있는 클로저를 넘기면 된다. use std::thread;use std::time::Duration; fn main() { thread::spawn(|| {
BPF ring buffer
bpf
BPF 프로그램은 수집한 데이터를 후처리하고 로깅하기 위해 정보를 User space로 전송하는데, 대부분의 경우 이를 위해 BPF Perf buffer(Perfbuf)를 사용한다. Perfbuf는 CPU마다 하나씩 생성되는 순환 버퍼로, Kernel space와 Use space간 데이터를 효율적으로 교환할 수 있도록 한다. 하지만 Perfbuf에는 두가지의 문제점이 있었다. 각 CPU에 대해 별도의 버퍼를 사용하기 때문에 데이터 스파이크에 대응하기 위해서 각각의 버퍼크기를 크게 할당해주어야 한다. 이 때문에 필요한 것 보다 더 많은 메모리 공간이 낭비될 수 있다. 연관된 이벤트가 서로 다른 CPU에서 빠르게 발생하는 경우 이벤트가 순서대로 전달되지 않을 수 있다. 이 때문에 이벤트를 옳은 순서로
X window
etc
X Window는 컴퓨터 그래픽 사용자 인터페이스(GUI)를 제공하기 위한 Unix, Linux 계열 운영 체제에서 사용되는 시스템이다. X Window 시스템은 네트워크 환경에서 그래픽 화면을 표시하고 입력 장치와 상호 작용할 수 있는 기능을 제공한다. X window의 구조라고 한다. 특징 클라이언트-서버 모델: X 클라이언트는 X 서버에서 동작하면서 서버에게 명령을 전달하고, X서버는 클라이언트에게 명령 요청의 결과를 디스플레이 장치에 출력해주거나 사용자 입력을 클라이언트에게 제공해주는 역할을 한다. 따라서 디스플레이 장치에 독립적이다. 모듈화: X Window 시스템은 모듈화되어 있으며, 다양한 그래픽 라이브러리와 툴킷을 사용하여 응용 프로그램을 개발할 수 있다. 이로 인해 다양한 스타일과
고루틴 스케줄링
go
Go 런타임은 프로그램이 실행되는 내내 고루틴을 관리한다. Go 런타임은 모든 고루틴을 다중화된 스레드들에 할당하고 모니터링하며, 특정 고루틴이 블록되면 다른 고루틴이 실행될 수 있도록 교체하는 일을 반복한다. 이 말은 고루틴이 블록 되더라도 다중화된 스레드는 블록 되지 않는다는 것을 의미한다. CPU Core가 존재하고 있으며 OS Scheduler에 의해서 다수의 Thread가 Scheduling되어 동작하고 있는 모습을 나타내는 그림이다. Network Poller는 Network를 처리하는 별도의 독립된 Thread를 의미한다. Run Queue에는 GRQ (Global Run Queue)와 LRQ (Local Run Queue)가 2가지가 존재한다. GRQ는 의미 그대로
메모리 관리
go
Go는 힙에서 동적 할당이 필요한 메모리를 암묵적으로 할당한다. 할당이 암묵적으로 이뤄지기 때문에 코딩이 쉽지만, 메모리 할당과 해제가 명확하지 않으니 메모리 사용량이 높아질 수 있는 부분을 놓칠 가능성이 있다. Go는 참조 지향이 아닌 값 지향적 언어이다. Go 변수는 절대 객체를 참조하지 않고, 항상 객체의 전체 값을 저장한다. (포인터가 없다는 의미는 아니다.) 모든 변수 선언(함수 인자, 반환 인자, 메서드 리시버 포함)은 해당 타입 전체를 할당하거나 그 포인터만 할당한다. new(&x3C;type>)은 &x26;&x3C;type>과 동일하며, 힙 상의 포인터 박스와 별도의 메모리 블록에 타입을 할당한다. Go 할당자는 특정 스팬에 하나 혹은 여러 8KB 페이지를 포함하는 메모리
JAVA
java
객체 지향 프로그래밍(OOP, Object-Oriented Programming) 모든 데이터를 객체(object)로 취급하여 객체의 상태와 행동을 구체화 하는 형태의 프로그래밍 클래스 (class) 객체를 정의하는 틀 또는 설계도 필드 = 클래스에 포함된 변수 메소드 = (class에 종속된) 함수 static 클래스 변수 혹은 클래스 메소드 앞에 붙는거 인스턴스 변수와 다르게 인스턴스하지 않아도 그냥 사용가능 (클래스가 메모리에 올라갈 때 메소드 영역에 바로 저장 되기 때문) A라는 클래스 안에 num이라는 static 변수가 있으면 그냥 A.num하고 쓰면 됨 함수도 그냥 메소드 이름.하고 파라미터만 넣어서 씀 반면, 인스턴스 변수는 new 해서 인스턴스로 만든담에 힙 영역에 저장돼야 사용 가
JDKProxy와 CGLibProxy
java
Proxy를 구현한 것 중 가장 많이 쓰이는 종류로는 JDK Proxy와 CGLib Proxy가 있다. 두 방식의 가장 큰 차이점은 Target의 어떤 부분을 상속 받아서 프록시를 구현하느냐에 있다. JDK Proxy는 Target의 상위 인터페이스를 상속 받아 프록시를 만든다. 따라서 인터페이스를 구현한 클래스가 아니면 의존할 수 없다. Target에서 다른 구체 클래스에 의존하고 있다면, JDK 방식에서는 그 클래스(빈)를 찾을 수 없어 런타임 에러가 발생한다. 우리가 의무적으로 서비스 계층에서 인터페이스 -XXXXImpl 클래스를 작성하던 관례도 다 이러한 JDK Proxy의 특성 때문이기도 하다. 또한 내부적으로 Reflection을 사용해서 추가적인 비용이 발생한다. public class Exa
Heap 영역 구조와 GC
jvm
런타임 데이터 영역은 크게 Method영역, Heap영역, Stack영역 등등으로 나뉘어있는데, 런타임중 가장 많은 메모리가 새로 할당되는 영역이 Heap영역이기 때문에, GC 또한 Heap영역을 위주로 실행된다. 이때, Heap 영역은 GC와 메모리 관리를 위해 저장되어있는 데이터를 내부에서 여러 유형으로 분류하여 저장한다. Heap영역은 크게 3가지의 영역으로 나뉜다. Young Generation 영역 자바 객체가 생성되자마자 저장되는 영역이다. 이름 그대로 생긴지 얼마 안되는 어린 객체들이 속하는 곳이다. Heap 영역에 객체가 생성되면 그 즉시 Young Generation 중에서도 Eden 영역에 할당되고, 이 영역에 데이터가 어느정도 쌓이게 되면 참조정도에 따라 Servivor의 빈 공간으로
JVM 구성요소
jvm
JVM 구성요소는 아래와 같은 것들이 있다. 클래스 로더(Class Loader) 실행 엔진(Execution Engine) 인터프리터(Interpreter) JIT 컴파일러(Just-in-Time) 가비지 콜렉터(Garbage collector) 런타임 데이터 영역 (Runtime Data Area) 각각에 대해서 자세히 알아보자. 클래스 로더 JVM 내로 클래스 파일(*.class)을 로드하고, 링크를 통해 배치하는 작업을 수행하는 모듈이다. 런타임시 동적으로 클래스를 로드하고 jar 파일 내에 저장된 클래스들을 JVM 위에 탑재한다. 즉, 클래스를 처음으로 참조할 때, 해당 클래스를 로드하고 링크하는 역할을 한다. 실행 엔진 클래스 로더가 JVM내의 런타임 데이터 영역에 바이트 코드를 배치시
Permanent to Metaspace
jvm
JAVA8에서부터, Permanent가 사라지고 Metaspace가 생김으로써 그 역할을 일부 대체하게 되었다. Permanent는 JVM에 의해 크기가 강제되었지만, Metaspace는 OS가 자동으로 크기를 조절할 수 있는 Native memory 영역이기 때문에 기존과 비교해 큰 메모리 영역을 사용할 수 있게 되었다. Perm 영역에는 주로 클래스, 메소드 정보와 클래스 변수의 정보, static 변수와 상수 정보들이 저장되었는데, 이게 Metaspace로 대체되면서 Perm에 있었던 대부분의 정보가 Metaspace에 저장되도록 바뀌었다. 다만, 기존 Perm 영역에 존재하던 static Object는 Heap 영역으로 옮겨져서 최대한 GC의 대상이 될 수 있도록 하였다고 한다. The propos
Runtime Data Area
jvm
런타임 데이터 영역(Runtime Data Area)은 JVM이 자바 프로그램 실행을 위한 데이터와 명령어를 저장하기 위해 OS로부터 할당받는 메모리 공간이다. Runtime Data Area는 크게 Method영역, Heap영역, Stack영역, PC 레지스터 영역, Native Method Stack으로 나눌 수 있다. Method 영역 클래스 로더에 의해 로드된 클래스, 메소드 정보와 클래스 변수의 정보가 저장되는 영역이다. 프로그램 시작부터 종료될때까지 메모리에 적재되지만 명시적 null 선언시 GC가 청소하도록 만들 수 있다. 데이터가 가장 먼저 저장되는 영역이며, 모든 스레드가 공유한다. Heap 영역 런타임시 결정되는 참조 자료형이 저장되는 영역이다. new 연산자를 통해 생성
메모리누수
jvm
CS적으로 보면, 컴퓨터 프로그램이 필요하지 않은 메모리를 계속 점유하고 있는 현상이다. 할당된 메모리를 사용한 다음 반환하지 않는 것이 누적되면 메모리가 낭비된다. 즉, 더 이상 불핑요한 메모리가 해제되지 않으면서 메모리 할당을 잘못 관리할때 발생한다. 자바에서 메모리 누수 더이상 사용되지 않는 객체들이 GC에 의해 회수되지 않고 계속 누적되는 현상을 말한다. 메모리 누수가 생기면 Old 영역에 계속 누적된 객체로 인해 Major GC가 빈번하게 발생하게 되면서, 프로그램 응답 속도가 늦어지고 성능이 저하된다. 이는 결국 OutOfMemory Error로 프로그램이 종료되게 한다. 가비지 컬렉션을 소멸 대상이 되기 위해서는 어떠한 reference 변수에서 가르키지 않아야 한다. 다 쓴 객체에 대한 참조를
예외와 에러
java
프로그래밍에서 예외(Exception)란 입력 값에 대한 처리가 불가능하거나, 프로그램 실행 중에 참조된 값이 잘못된 경우 등 정상적인 프로그램의 흐름을 어긋나는 것을 말한다. 그리고 자바에서 예외는 개발자가 직접 처리할 수 있기 때문에 예외 상황을 미리 예측하여 핸들링할 수 있다. 한편, 에러(Error)는 시스템에 무엇인가 비정상적인 상황이 발생한 경우에 사용된다. 주로 자바 가상머신에서 발생시키는 것이며 예외와 반대로 이를 애플리케이션 코드에서 잡으려고 하면 안 된다. 에러의 예로는 OutOfMemoryError, ThreadDeath, StackOverflowError 등이 있다. Checked Exception과 Unchecked Exception Exception은 다시 Check
프로토타입
javascript
JavaScript에는 객체라는 구조가 존재하고, 각 객체에는 다른 객체에 대한 링크를 보유하는 프로토타입이라는 비공개 속성이 있다. 그 프로토 타입 객체도 자신만의 프로토타입을 가지고 있으며, 프로토타입으로 null을 가진 객체에 도달할 때까지 이 연결은 계속된다. 예시 코드 닭의 프로토타입을 참새로 지정하면, 닭의 날개갯수와 날수있나 값을 참조했을 때 참새가 가지고 있던 값과 동일한 값이 반환된다. 이떄 날수있나 값을 false로 재지정하면 값이 바뀌게 된다. function 참새(){ this.날개갯수 = 2; this.날수있나 = true;}const 참새1 = new 참새();console.log("참새의 날개 갯수 : ", 참새1.날개갯수); // 2 function 닭() { th
화살표 함수
javascript
ES6가 도입되면서, js에 화살표 함수라는 문법이 등장했다. 화살표 함수는 말 그대로 화살표(=>) 표시를 사용해서 함수를 선언하는 방법이다. // 기존 함수const foo = function () { console.log('기존 함수');} // 화살표 함수const foo = () =console.log('화살표 함수'); console.log(&x27;화살표 함수&x27;);"> 두 코드는 기능적으로 완전히 동일하게 작동한다. 그러나, 두 코드는 this 바인딩에서 차이가 있다. this 바인딩 JS의 this는 상황에 따라 다르게 바인딩 된다. 대표적으로 this에 바인딩되는 값들은 이렇다. 전역 공간의 this : 전역 객체메소드 호출 시 메소드 내부의 this : 해당 메소드를 호출한 객체함
InlineFuntion과 Reified
kotlin
inline 키워드는 자바에서는 제공하지 않는 코틀린만의 키워드이다. 코틀린 공식문서의 inline function을 보면, 코틀린에서 고차함수(High order functions, 함수를 인자로 전달하거나 함수를 리턴)를 사용하면 패널티가 발생한다고 나와있다. 패널티란 추가적인 메모리 할당 및 함수호출로 Runtime overhead가 발생한다는 것으로, 람다를 사용하면 각 함수는 객체로 변환되어 메모리 할당과 가상 호출 단계를 거치는데 여기서 런타임 오버헤드가 발생한다. inline functions는 내부적으로 함수 내용을 호출되는 위치에 복사하며, Runtime overhead를 줄여준다. 객체로 변환되는 오버헤드란? 아래와 같은 고차함수(함수를 인자로 전달하거나 함수를 리턴하는 함수)를 컴파일 하
람다 표현식
kotlin
람다는 익명 함수이며, 함수형 프로그래밍에서 자주 사용하는 패턴이다. 코틀린은 객체지향 프로그래밍 뿐만 아니라 함수형 프로그래밍 또한 지원하는 언어이기 때문에 당연히 람다 표현식을 사용할 수 있다. 익명함수 생성 익명함수는 아래처럼 이름없이 정의되는 함수를 말한다. 변수 printHello에 할당되고 있는 내용이 바로 익명함수이다. // 익명함수를 생성하여 printHello에 할당 val printHello = fun(){ println("Hello, world!") } // 익명함수 호출 printHello() 실행결과 Hello, world! 람다를 이용하면 더 간단히 익명함수를 정의할 수 있다. 아래는 위와 동일한 코드를 람다로 재작성 한 것이다. // 익명함수를 생성하
Nullable
변수
Kotlin에서는 코틀린은 원시 타입(primitive type)과 래퍼 타입(wrapper type)을 따로 구분하지 않고, Null일 수 있는 타입과, Null이 불가능한 타입으로 나누어 사용한다. 널이 될 수 있는지 여부를 타입 시스템을 통해 확실히 구분함으로써 컴파일러가 여러 가지 오류를 컴파일 시 미리 감지해서 실행 시점에 발생할 수 있는 예외의 가능성을 줄일 수 있다. 또, null 처리를 위한 다양한 연산자를 지원한다. NULL이 될 수 있는 타입 ? !! 코틀린의 모든 타입은 기본적으로 널이 될 수 없는 타입이다. 타입 옆에 물음표(?)를 붙이면 널이 될 수 있음을 뜻한다. 느낌표 2개(!!)를 변수 뒤에 붙이면 NULL이 될 수 있는 타입의 변수이지만, 현재는 NULL이 아님을 나타낼 수
Object
클래스
코틀린에서 클래스를 정의하는 키워드는 class이다. 하지만 간혹 object 키워드로 클래스 정의하는 경우를 볼 수 있다. object로 클래스를 정의하면, 싱클턴(Singleton) 패턴이 적용되어 객체가 한번만 생성되도록 한다. 코틀린에서 object를 사용하면 싱글톰을 구현하기 위한 Boiler plate를 작성하지 않아도 된다. 또는, 익명 객체를 생성할 때 쓰이기도 한다. object의 용도 싱글턴 클래스로 만들 때 익명 클래스 객체를 생성할 때 싱글턴 클래스 정의를 위한 Object 아까도 말했듯, object로 싱글턴 클래스를 정의할 수 있다. 원래 클래스를 정의할때 class가 있는 자리에 object를 입력해주면 이 클래스는 싱글턴으로 동작하게 된다. object CarFactory {
클래스 상속
클래스
상속은 클래스의 기능을 확장하고자 할때 현재의 클래스의 기능을 모두 가지고 자신만의 기능이 추가된 새로운 클래스를 정의 하는 방법이다. 따라서 상속을 하게 되면 클래스가 상, 하의 계층구조를 가지게 된다. 코틀린에서 모든 클래스는 공통의 상위클래스(superclass)로 Any 클래스를 가진다. 클래스에 상위 클래스를 선언하지 않아도 기본적으로 Any가 상위 클래스가 된다. 마치 JAVA에서 Object가 클래스의 기본 상위 클래스가 되는 것괴 비슷하다. 하지만 클래스 내용이 같지는 않다. Any와 Object 비교 Kotlin의 Any보다 Java의 Object가 가지는 메서드의 수가 더 많다. public open class Any { public open operator fun equals(
구조체 impl
rust
Rust에서 데이터를 표현하는 구조체(혹은 enum, trait 객체)의 맥락에서 그 구조체와 연관된 함수들을 정의할 수 있는데, 이렇게 연관되어진 함수들을 메서드라 한다. 메서드는 맥락이 되는 구조체 인스턴스로부터 호출되어 사용된다. Rust에서 구조체(struct)에 메서드들을 구현하는 구현 블럭(implementation block)은 “impl” 키워드를 사용하여 정의된다. impl 구현블럭 impl 키워드는 구현 블럭(implementation block)을 정의할 때 사용하는데, impl 뒤에 타입명을 적고 impl 블럭 안에 메서드(method) 혹은 연관 함수(associated function)를 넣게 된다. impl 안에 정의된 함수는 그 타입과 연관된 함수라는 의미에서 Associated
Rc 타입과 Weak 타입
메모리 참조
소유권 규칙에 따라 Rust에서 어떤 값은 여러 소유자를 가질 수 없다. Reference Counted를 의미하는 Rc는 힙 메모리에 할당된 타입 T 값의 소유권을 공유할 수 있게 해주는 타입이다. 즉, 스마트 포인터 Rc를 사용하면 타입 T의 값에 대한 여러 개의 소유자를 만들 수 있다. 기본적으로, Rc 타입은 Clone Trait을 구현하고 있고 clone을 호출해서 T 값에 대한 새로운 포인터를 생성하며, 모든 Rc 포인터가 해제되면 메모리에 할당된 T 값이 drop되는 구조이다. Rust에서 공유된 참조자는 수정할 수 없는데, Rc 타입 또한 예외가 아니며 일반적인 방법으로는 mutable한 참조를 얻을 수 없다. 만약, mutable 한 참조가 필요하면 Cell 타입이나 RefCel
소유권과 Lifetime
메모리 참조
기본적으로 모든 변수 바인딩은 유효한 “범위(스코프)“를 가지며, 범위 밖에서 변수 사용하면 에러가 발생한다. 스코프가 종료되면 변수는 “삭제(drop)“되었다고 하며 그 변수의 데이터는 메모리에서 해제된다. Rust에서는 스코프가 종료될 때 다른 리소스를 해제하기 위해 소멸자가 호출되도록 하는 것을 변수가 값을 소유한다고 정의한다. 러스트의 각각의 값은 해당값의 오너(owner)라고 불리우는 변수를 갖고 있으며 한번에 딱 하나의 오너만 존재할 수 있다. fn main() { let s1: String = String::from("Rust"); let s2: String = s1;} 위 코드는 "Rust"라는 String 값에 대한 소유권을 s1에서 s2로 이전한다. s2에 s1을 대입
스마트 포인터 활용
메모리 참조
스마트 포인터(Smart Pointer)는 포인터처럼 작동하지만 추가적인 메타데이터와 능력들도 가지고 있는 데이터 구조이다. String과 Vec&x3C;T>는 스마트 포인터이다. 스마트 포인터는 보통 구조체를 이용하여 구현되어 있다. 스마트 포인터가 일반적인 구조체와 구분되는 특성은 스마트 포인터가 Deref와 Drop 트레잇을 구현한다는 것이다. Deref 트레잇은 스마트 포인터 구조체의 인스턴스가 참조자처럼 동작하도록 하여, 참조자나 스마트 포인터 둘 중 하나와 함께 작동하는 코드를 작성하게 해준다. 스마트 포인터가 평범한 참조자처럼 취급될 수 있도록 구현한다. Deref를 구현한 구조체에 대해 *로 값을 참조하면, deref 함수를 호출한 후 *를 한번 호출하는 것으로 대치된다.
직렬화 serialVersionUID
언어
가끔 자바코드에서 이런 코드를 발견할 때가 있다. private static final long serialVersionUID = 3487495895819393L; 이 serialVersionUID라는 long 타입의 상수는 직렬화할 객체의 버전이 바뀌었는지 식별하기 위한 클래스의 고유 식별자이다. 직렬화와 역직렬화 할때 이 값이 동일하면 동일한 클래스의 데이터라는 것을 확인할 수 있고, 그렇지 않은 경우에는 다르거나 바뀐 클래스라고 생각하여 오류를 throw할 수 있다. 자바 스펙에 따르면, serialVersion을 명시적으로 선언해놓지 않았을 땐 직렬화 런타임이 기본 serialVersion을 클래스의 기본 해쉬값을 가지고 자동으로 계산해준다고 한다. 하지만 JVM에 의한 default ser
쉘 단축키
linux
커서 이동하기 Ctrl + A: 현재 입력중인 라인의 시작 위치로 이동한다. Ctrl + E: 현재 입력중인 라인의 마지막 위치로 이동한다. Ctrl + XX: 현재 입력중인 위치와 라인의 시작 위치를 번갈아 이동한다. Alt + F: 현재 입력중인 라인에서 한 단어를 건너뛰어 이동한다. Alt + B: 현재 입력중인 라인에서 앞쪽으로 한 단어를 건너뛰어 이동한다. Ctrl + F: 현재 입력중인 라인에서 한 글자 앞으로 이동한다. Ctrl + B: 현재 입력중인 라인에서 한 글자 뒤로 이동한다. 텍스트 조작 Ctrl + U: 현재 입력중인 라인의 현재 위치부터 라인의 처음까지를 잘라내어 클립보드에 저장한다. 만약 현재 위치가 라인의 마지막이라면, 전체 라인을 잘라내기한다. Ctrl + K: 현재 입력
vi 단축키
vi
커서 이동 행 k : 커서를 한 행 위로 이동 j : 커서를 한 행 아래로 이동  - : 커서를 앞 행의 처음으로 이동 + : 커서를 다음 행의 처음으로 이동  ^ 또는 0 : 커서를 현재 행의 맨 처음으로 이동 $ : 커서를 현재 행의 마지막으로 이동     글자 l : 커서를 한 글자 오른쪽으로 이동 h : 커서를 한 글자 왼쪽으로 이동  단어 w : 커서를 다음 단어의 첫 글자로 이동 b : 커서를 앞 단어의 첫 글자로 이동 화면 이동하기 반 화면 Ctrl + u : 반 화면 위로 이동 Ctrl + d : 반 화면 아래로 이동 한 화면 Ctrl + b : 한 화면 위로 이동  Ctrl + f : 한 화면 아래로 이동 행 Ctrl + y : 화
Cramfs
embedded
Cramfs (Compressed ROM File System)는 플래시 디바이스 내부에서 사용 가능한 압축된 읽기 전용 리눅스 파일 시스템이다. 간단하고 공간 효율적이다. zlib 루틴을 사용해 파일을 한 페이지씩 압축하고 랜덤 페이지 접근을 허용한다. 메타데이터는 압축되지 않지만 매우 간결한 표현을 사용해 기존 파일시스템보다 디스크 공간을 훨씬 적게 사용한다. 메모리 크기가 작은 임베디드 디자인에 활용된다. 현재 시스템에서 사용자 어플리케이션 실행폴더로 활용 RAM과 다르게 중간에 전원이 꺼지더라도 파일시스템이 훼손되지 않는다. cramfs 파일시스템에는 쓰기가 불가능하다 (높은 압축률 때문에 실시간 업데이트가 매우 어렵다). 따라서 별도 유틸리티로 디스크 이미지를 생성해야 한다.
Athena
analytics
Amazon Athena는 오픈 소스 프레임워크를 기반으로 구축된 서버리스 대화형 분석 서비스로, 오픈 테이블 및 파일 형식을 지원한다. 페타바이트 규모의 데이터를 분석할 수 있는 간단한 방법을 제공한다. Athena를 사용하면 SQL 또는 Python을 사용하여 Amazon Simple Storage Service(S3) 데이터 레이크와 온프레미스 데이터 소스나 다른 클라우드 시스템을 포함한 30개의 데이터 소스에서 데이터를 분석하거나 애플리케이션을 구축할 수 있다. 오픈 소스 Trino 및 Presto 엔진과 Apache Spark 프레임워크를 기반으로 구축되어 있으며, 프로비저닝이나 구성 작업 없이 사용할 수 있다. SQL용 Amazon Athena는 AWS Management Conso
KMS
security
KMS는 Key Management Service의 약자로, 데이터를 암호화 할떄 사용되는 암호화 Key를 안전하게 관리하는데 목적을 둔 AWS의 서비스이다. KMS는 크게 세가지 방식으로 key 관리 서비스를 제공한다. AWS managed key AWS 서비스들이 내부적으로 발급받는 Key로, 내부적으로 자동으로 일어나게 되며 사용자가 직접적으로 제어가 불가능하다. 자신의 AWS 계정에 들어가면 만들어진 Key의 목록을 확인하는건 가능하다. (참고) 모든 AWS managed keys는 1년마다 rotate된다. 이 주기는 사용자가 변경할 수 없다. Customer managed key(CMK) 사용자가 직접 key를 생성하고 관리하는 것이다. CMK에 대해서는 IAM을 통해 권한을 부여받아 제
CI/CD파이프라인
devops
CI(Continuous Integration) CI는 지속적 통합이라는 뜻으로 여러 명이 하나의 코드에 대해서 수정을 진행해도 지속적으로 통합하면서 충돌 없이 작업, 관리할 수 있음을 의미한다. 또한, 공유 버전 관리 레포지토리에 통합되어 있는 코드에 대해, 자동화된 테스트를 진행하여 통합된 코드에서 생기는 문제를 신속하게 파악하고 해결할 수 있도록 하는 것이 CI의 특징이다. CD(Continuous Delivery/Deployment) CD는 지속적인 제공또는 지속적인 배포를 모두 의미한다. 두 가지 모두 파이프라인의 추가 단계에 대한 자동화를 뜻하지만, 자세한 개념은 다르다. 지속적인 제공(Continuous Delivery) 지속적인 제공은 개발자들이 애플리케이션에 적용한 변경사항이 버그 테스
CNI
cni
container를 돌리는 모든 소프트웨어들은(ex. docker, rkt, mesos, k8s) 각 컨테이너간의 네트워크를 구현한다. 그것은 모두 네트워크 네임스페이스를 통해 구현되고, 서로 비슷한 절차를 거쳐 브릿지를 생성한다. 약간의 차이는 있을 수 있지만 전반적인 흐름은 아주 유사하다. 그렇다면 그 작업을 표준화한 인터페이스를 만든다면 어떨까? 이를 위해 정의된 것이 바로 CNI(Container Network Interface)이다. CNI는 컨테이너 네트워크 작업을 수행하는 코드가 대략적으로 어떤 동작을 해야하고, 어떻게 호출되어야햐는지를 정의한다. 컨테이너를 돌리는 소프트웨어는 CNI 스펙에 맞추어 함꼐 동작할 수 있도록 구현됐기 때문에 해당 Interface를 구현하는 구현체중 원하는 것을
Calico
cni
Calico는 Kubernetes 기반 워크로드와 비-Kubernetes 또는 레거시 워크로드 간의 안전하고 원활한 통신을 가능하게 하는 네트워크 및 보안 솔루션이다. Kubernetes에서는 기본적으로 모든 Pod 간 네트워크 트래픽이 허용되어 모든 Pod가 서로 자유롭게 통신할 수 있다. Calico는 네트워크 계층의 보안을 강화하고, 대규모 클라우드 네이티브 애플리케이션을 보호하기 위한 고급 네트워크 정책을 제공한다. 구성 요소 Calico CNI (Container Network Interface) Calico CNI는 여러 데이터플레인을 제어하는 컨트롤 플레인이다. L3/L4 계층의 네트워크 솔루션으로, 컨테이너, Kubernetes 클러스터, 가상 머신, 호스트 기반 워크로드 간의 안전한 통신을
Container Orchestration
container
레드햇(Red Hat)의 정의에 따르면, IT 업계에서 오케스트레이션(Orchestration)이란 용어는 “컴퓨터 자원과 어플리케이션, 서비스에 대한 자동화된 설정, 관리 및 제어 체계”를 의미한다. 비슷한 느낌으로 컨테이너 오케스트레이션은, "컨테이너화 된 애플리케이션에 대한 자동화된 설정, 관리 및 제어 체계"로 받아들일 수 있다. 컨테이너 오케스트레이션이 필요한 이유 단일 호스트로 구성된 환경은 확장성(Scalability)과 가용성(Availabilty), 그리고 장애 허용성(Fault Tolerance) 측면에서 많은 한계점을 가지기 때문에, 애플리케이션을 여러개의 호스트로 나누어 구축해야하는 경우가 많다. 마이크로서비스 아키텍처(MSA; Microservice Architecture)에서는 프
ContainerRuntime
container
컨테이너를 쉽게 다운로드받거나 공유하고 구동할 수 있게 도와주는 툴 컨테이너를 실행하기 위해서는 다음과 같은 세 단계를 거쳐야한다. 즉, 컨테이너 런타임은 이러한 단계들을 실행해주는 기능을 가진다. 런타임은 실제 컨테이너를 실행하는 단계만 수행하는 저수준 컨테이너 런타임(OCI 런타임)과 컨테이너 이미지의 전송 및 관리, 이미지 압축 풀기 등을 실행하는 고수준 컨테이너 런타임으로 나뉜다. 컨테이너를 실행하려면 저수준 및 고수준 컨테이너 런타임이 각각의 역할을 해야한다. 즉, 컨테이너를 실행하려면 두 런타임이 모두 있어야한다. 저수준 컨테이너 런타임(Low-Level Container Runtimes) 컨테이너는 Linux namespace와 cgroup을 사용하여 구현한다. namespace : 각 컨
DockerSwarm
docker
Docker Swarm은 도커에서 자체적으로 제작한 컨테이너 오케스트레이션 도구이다. Docker Swarm을 사용한다면 여러 컨테이너의 배포를 관리하고, 네트워크 및 컨테이너 상태를 제어 및 모니터링 할 수 있다. 쿠버네티스와의 차이? 컨테이너 오케스트레이션을 위한 툴로는 여러가지가 있는데 그중 가장 널리 쓰이는 것은 쿠버네티스로, 사실상 표준 기술로 자리잡았다 볼 수 있을 정도로 널리 쓰이고 있다. 하지만 도커 스웜(Docker Swarm)은 Mirantis가 Docker의 엔터프라이즈 플랫폼 사업을 인수한 이래로 유지보수 단계에 접어들어 더 이상의 발전과 기능 추가를 기대할 수 없게 되었다. 그렇다면 도커 스웜보다는 쿠버네티스를 배우는게 좋지 않을까? 굳이 도커 스웜을 사용해야하는 이유가 뭘까? 도커
Prune
docker
Docker를 오랜 시간 사용하게 되면 여러가지 오브젝트들이 시스템에 쌓이게 된다. 컨테이너나 이미지는 많으면 수십 수백개까지도 늘어난다. Docker 컨테이너, 이미지, 볼륨은 사용중이 아니더라도 디스크를 차지하고 있다. 오브젝트들을 일일히 삭제하거나 통째로 날려버릴 수도 있지만, 사용하지 않는 오브젝트들을 파악해 빠르게 시스템 자원을 확보하는 방법도 있다. prune 서브 커맨드가 바로 이런 역할을 한다. Prune 커맨드를 사용하면 사용하지 않는 컨테이너, 볼륨, 이미지를 일괄적으로 삭제할 수 있다. container docker container prune --filter 옵션으로 특정 오브젝트만 삭제할 수도 있다. 중지된 지 1시간 이상 지난 컨테이너만 삭제docker container prune
README
docker
도커는 LXC(리눅스 컨테이너스)라는 커널 컨테이너 기술을 이용하여 만든 컨테이너 기술 중 하나로, 컨테이너 기반의 오픈소스 가상화 플랫폼이다. 컨테이너를 모듈식 가상머신처럼 유연하게 사용하여 애플리케이션을 안정적으로 배포 및 구축할 수 있도록 한다. 또, 이미지 기반 배포 모델을 제공하고 여러 환경 전반에서 애플리케이션 또는 서비스를 모든 종속 항목과 손쉽게 공유할 수 있다. 운영체제를 가상화하지 않는 컨테이너 기술이기 때문에 가상머신에 비해 가볍고, 한 대의 서버에 여러 애플리케이션을 실행하기 좋다. 단일한 물리적 컴퓨터 위에서 여러 애플리케이션을 돌릴 수 있기 때문에 물리적 하드웨어의 컴퓨팅 용량을 효율적으로 사용할 수 있다. 가상머신(VM)들과 달리, 기존 리눅스 자원(디스크, 네트워크 등)을 그대로
가상화와 컨테이너
docker
가상화 가상화는 단일 컴퓨터의 프로세서, 메모리, 스토리지 등과 같은 하드웨어 요소를 가상 머신(VM, Virtual Machine)이라고 하는 다수의 가상 컴퓨터로 분할할 수 있도록 해주는 추상화 계층을 구축하는 기술을 말한다. 실제로는 컴퓨터의 일부에서만 실행됨에도 불구하고, 각각의 VM은 자체적으로 운영체제(Guest OS)를 실행하며 마치 여러개의 컴퓨터인 것 처럼 독립적으로 작동된다. ✔️가상화의 장점 1. 리소스 효율성 가상화 이전에는 애플리케이션마다 별도의 서버를 구성해야했다. 그렇기 때문에 한 애플리케이션이 유휴상태에 있을때는 서버가 활용되지 못한 채 방치된다. 하지만 서버 가상화를 사용하면 단일한 물리적 컴퓨터 위에서 여러 애플리케이션을 돌릴 수 있기 때문에 물리적 하드웨어의 컴퓨팅 용량을
도커 네트워크
docker
Docker 컨테이너(container)는 격리된 환경에서 돌아가기 때문에 기본적으로 다른 컨테이너와의 통신이 불가능하다. 하지만 여러 개의 컨테이너를 하나의 Docker 네트워크(network)에 연결시키면 서로 통신이 가능해잔다. 다시말해, Docker 네트워크는 컨테이너 간 네트워킹이 가능하도록 도와주는 역할을 한다. 네트워크 종류 Docker는 목적에 따라 다양한 종류의 네트워크 드라이버를 지원한다. 그 종류에 대해 알아보자. none none 네트워크에서 도커 컨테이너는 서로 독립되어서, 정보를 전혀 주고받을 수 없다. 호스트 외부로 접근하는 경우에도 네트워크가 연결되지 않는다. host host 네트워크에서는 host와 컨테이너가 네트워크의 구분 없이 서로 면결된다. 만약 컨테이너가 80
도커 스토리지
docker
여러 작업 중 컨테이너 내부에서 생성한 정보, 파일은 컨테이너가 종료된 후에 모두 사라진다. 이러한 데이터를 저장하려면 별도의 저장공간이 필요한데, 컨테이너가 동작 중인 상태에서는 접근이 제한되기 때문에 직접 옮기기는 쉽지 않다. 도커는 스토리지에 파일을 저장하여 컨테이너가 종료되더라도 파일을 유지할 수 있도록 한다. 스토리지는 원본 이미지를 수정 하는 대신 변경된 정보를 따로 저장하고, 원본 데이터와 변경된 정보를 조합해서 복원하는 식으로 데이터를 읽는다. 이렇게 하여 원본 이미지를 수정 할 필요 없이 각 컨테이너마다 다른 정보를 저장 할 수 있다. 스토리지 종류 도커 스토리지의 종류는 3가지가 있다. Volume, bind mount, tmpfs mount이다. 아래 그림은 각 방식을 나타내는 그림이다.
도커 안에서 도커 사용하기
docker
도커를 사용하다보면 모종의 목적으로 도커 컨테이너 안에서 도커를 사용할 일이 생길 수 있다. 이것을 Docker in Docker (DinD)라고 부르는데, 이를 위한 방법은 크게 2가지로 나뉜다. 호스트의 도커 데몬을 사용(마운트)하여 도커 컨테이너 내부에서 호스트의 도커 데몬을 사용하는 방법 도커 컨테이너 내부에서 ‘실제’ 도커를 사용하는 방법 1. 도커 컨테이너 내부에서 호스트의 도커 데몬을 사용하는 방법 이 방법은 도커 컨테이너 내부에서 도커를 사용할 때, 도커 컨테이너 내부의 도커가 아닌, 호스트의 도커 데몬을 사용해서 도커를 사용하는 방법이다. 도커 데몬에게 명령을 내릴 수 있는 인터페이스인 ‘docker.sock’ 파일을 마운트해서 실행하면 된다. 이렇게 설정해주면 도커 컨테이너 내부의 도커
cAdvisor
container
Kubernetes(k8s)에서 cAdvisor는 “Container Advisor”의 줄임말로, 컨테이너 메트릭을 수집하고 모니터링하기 위한 도구이다. cAdvisor는 Google에서 개발한 오픈 소스 프로젝트로, 컨테이너화된 환경에서 작동하는 애플리케이션 및 서비스의 성능을 실시간으로 추적하고 이해하는 데 도움을 준다. 주 기능 컨테이너 메트릭 수집: cAdvisor는 호스트 시스템에서 실행 중인 각 컨테이너에 대한 메트릭을 수집한다. 이 메트릭은 CPU 사용량, 메모리 사용량, 디스크 I/O, 네트워크 사용량 및 다른 성능 관련 정보를 포함한다. 시각화: cAdvisor는 수집된 메트릭을 시각적으로 표시하여 사용자가 컨테이너의 성능과 리소스 사용 상태를 쉽게 이해할 수 있도록 도와준다. 리소스 모니
DR strategies
dr
DR(재해 복구)은 비즈니스 연속성 계획의 핵심 요소이다. 재해에 대비하고 복구하는 과정인 DR을 위해 어떻게 아키텍처를 설계할 수 있을까? 재해 이벤트는 워크로드를 중단시킬 수 있기 때문에, DR의 목표는 워크로드를 다시 가동하거나 다운타임을 완전히 방지하는 것이어야 한다. 이를 위해 다음과 같은 목표 지표를 사용한다: Recovery Time Objective (RTO): 서비스 중단부터 서비스 복원까지 허용 가능한 최대 지연 시간이다. 허용 가능한 서비스 다운타임 길이를 결정한다. Recovery Point Objective (RPO): 마지막 데이터 복구 시점 이후 허용 가능한 최대 시간이다. 허용 가능한 데이터 손실량을 결정한다. RTO와 RPO는 숫자가 낮을수록 다운타임과 데이터 손실이 적다
Fail over와 서버 이중화
dr
Fail over fail over는 장애 대비 기능을 의미한다. 컴퓨터 서버, 시스템, 네트워크 등에서 이상이 생겼을 때 미리 준비했던 다른 시스템으로 자동으로 전환해서 무정지 시스템을 운영하여 fail over할 수 있다. failback : 페일오버에 따라 전환된 운용환경을 장애 발생 전 상태로 되돌리는 처리 High Availability(서비스를 정상적으로 사용 가능한 정도를 의미)을 요구할 때 구성한다. 웹 서버, 네트워크 장비, DB 등 다양한 영역에 대비한다. 하드웨어적인 장애 뿐만 아니라 소프트웨어를 포함한 서비스가 운영되지 않은 모든 장애를 포함한다. 서버 이중화 Active-Active 주로 부하 분산 등의 목적, 서비스 단위를 나누어서 분산 다중화 장비 두 대가 모두 활성화 되어
Configuration Drift
iac
Configuration Drift는 수동적이고 임시방편적인 변경, 업데이트, 그리고 일반적인 엔트로피로 인해 인프라의 서버들이 시간이 지남에 따라 서로 점점 더 달라지는 현상이다. 자동화된 서버 프로비저닝 프로세스는 머신이 생성될 때 일관성을 보장하는 데 도움이 되지만, 특정 머신의 생명주기 동안 기준선(baseline)과 다른 머신들로부터 표류(drift)하게 된다. Configuration drift에 대응하는 두 가지 주요 방법이 있다. 하나는 Puppet이나 Chef와 같은 자동화된 구성 도구를 사용하여 머신을 일관되게 유지하기 위해 자주 반복적으로 실행하는 것이다. 다른 하나는 머신 인스턴스를 자주 재구축하여 기준선에서 표류할 시간을 주지 않는 것이다. Configuration drift가 발생하
Phoenix Server
iac
예전에 일반적으로 서버를 운영할때는 주로 서버를 설치한 후 OS를 설치한 후에, 필요한 소프트웨어와 애플리케이션을 설치하여 운영하였다. 여기에 문제가 생긴 경우 패치를 하거나 정기적인 보안 패치 튜닝들을 해당 서버에 지속적으로 적용하고, 애플리케이션은 CI/CD 등의 툴을 이용하여 배포하는 구조를 가지고 있었다. 이렇게 한번 설치한 서버에 계속해서 설정을 변경하고 패치를 적용하는 등의 업데이트를 지속적으로 적용하여 운영하는 서버를 Snowflakes Server라고 하는데, 이렇게 설정된 서버는 다시 똑같이 설정하기가 매우 어렵다. 모든 설정과정이 문서화가 잘되어 있으면 모르겠지만 대부분 문서화가 꼼꼼한 경우가 굉장히 드물고, 담당자가 바뀌거나 관리 조직이 바뀌는 경우에는 그 이력이 제대로 유지되는 경우가
K8s Architecture
kubernetes
쿠버네티스는 중앙(Master)에 API 서버와 상태 저장소를 두고 각 서버(Node)의 에이전트(kubelet)와 통신하는구조로 동작한다. 하지만 이 개념을 여러 모듈로 쪼개어 구현하고 다양한 오픈소스를 사용하기 떄문에 설치가 까다롭고 구성이 복잡해보일 수 있다. 마스터-노드 구조 쿠버네티스는 전체 클러스터를 관리하는 마스터와 컨테이너가 배포되는 노드로 구성되어있다. 모든 명령은 마스터의 API 서버를 호출하고 노드는 마스터와 통신하면서 필요한 작업을 수행한다. 특정 노드의 컨테이너에 명령하거나 로그를 조회할 때도 노드에 직접 명령하는게 아니라 마스터에 명령을 내리고 마스터가 노드에 접속하여 대신 결과를 응답한다. Master 마스터 서버는 다양한 모듈이 확장성을 고려하여 기능별로 쪼개져 있는 것이 특징이
Kubernetes
kubernetes
쿠버네티스(Kubernetes)는 컨테이너화 된 애플리케이션의 대규모 배포, 스케일링 및 관리를 간편하게 만들어주는 오픈 소스 기반 컨테이너 오케스트레이션 도구이다. 프로덕션 환경에서는 애플리케이션을 실행하는 여러 컨테이너를 관리하고 다운타임이 없는지 확인해야하는데, Kubernetes는 다중 컨테이너 처리를 자동으로 처리하고, 분산 시스템을 탄력적으로 실행할 수 있는 프레임워크를 제공한다. K8s를 사용하면 애플리케이션의 확장 및 장애 조치를 처리하고 배포 패턴 등을 쉽게 처리할 수 있다. 쿠버네티스의 특징 5가지 1. 선언적 접근 방식 쿠버네티스에서는 동작을 지시하는 개념보다는 상태를 선언하는 개념을 주로 사용한다. 쿠버네티스는 원하는 상태(Desired state)와 현재의 상태(Current sta
ServiceDNS
dns
생성된 서비스의 IP는 어떻게 알 수 있을까? 서비스가 생성된 후 kubectl get svc를 이용하면 생성된 서비스와 IP를 받아올 수 있지만, 이는 서비스가 생성된 후이고, 계속해서 변경되는 임시 IP이다. DNS를 이용하는 방법 가장 쉬운 방법으로는 DNS 이름을 사용하는 방법이 있다. 서비스는 생성되면 [서비스 명].[네임스페이스명].svc.cluster.local 이라는 DNS 명으로 쿠버네티스 내부 DNS에 등록이 된다. 쿠버네티스 클러스터 내부에서는 이 DNS 명으로 서비스에 접근이 가능한데, 이때 DNS에서 리턴해주는 IP는 외부 IP (External IP)가 아니라 Cluster IP (내부 IP)이다. 간단한 테스트를 해보자. hello-node-svc 가 생성이 되었는데, 클러스터내의
Network Troubleshooting
network
각 상황에 맞는 네트워크 트러블슈팅 도구를 정리하면 다음과 같다: 상황도구연결 확인traceroute, ping, telnet, netcat포트 스캔nmapDNS 레코드 확인dig, 연결 확인 도구들HTTP/1 확인cURL, telnet, netcatHTTPS 확인OpenSSL, cURL리스닝 프로그램 확인netstat 보안 본격적으로 도구를 다루기 전에, 보안에 대해 먼저 인지해야 한다. 공격자는 여기 소개된 모든 도구를 이용해 시스템을 탐색하고 침투할 수 있다. 그래서 최선의 방법은 각 머신에 최소한의 네트워킹 도구만 설치하는 것이다. 물론 공격자가 직접 도구를 다운로드하거나 패키지 매니저를 쓸 수도 있다(권한이 있다면). 대부분의 경우 단지 공
eBPF
network
eBPF는 커널에서 샌드박스된 특별한 프로그램을 실행할 수 있게 해주는 프로그래밍 시스템이다. Netfilter나 iptables처럼 커널과 유저 공간을 오가지 않고 커널 내에서 직접 동작한다. eBPF 이전에는 BPF(Berkeley Packet Filter)가 있었다. BPF는 커널에서 네트워크 트래픽을 분석하는 데 사용되는 기술이다. BPF는 패킷 필터링을 지원하는데, 유저 공간 프로세스가 어떤 패킷을 검사할지 지정하는 필터를 제공할 수 있다. BPF의 대표적인 사용 사례가 tcpdump다. tcpdump는 필터를 BPF 프로그램으로 컴파일해서 BPF에 전달한다. BPF의 기법은 이후 다른 프로세스와 커널 작업으로 확장되었다. tcpdump 예제 Terminal window$ sudo tcpdump -
PV & PVC
object
k8s에서 Volume을 사용하는 구조는 PV라고 하는 퍼시스턴트 볼륨(PersistentVolume)과 PVC라고 하는 퍼시스턴트 볼륨 클레임(PersistentVolumeClaim) 2개로 분리되어 있다. PV/PVC PV는 Persistent Volume의 약자이다. pod와는 별개로 관리되며 별도의 생명 주기가 있다. PVC는 사용자가 PV에 하는 요청이다. 사용하고 싶은 용량은 얼마인지, 읽기/쓰기는 어떤 모드로 설정하고 싶은지 등을 정해서 요청한다. k8s 볼륨을 pod에 직접 할당하는 방식이 아니라 중간에 PVC를 두어 pod와 pod가 사용할 스토리지를 분리할 수 있다. 이런 구조는 pod 각각의 상황에 맞게 다양한 스토리지를 사용할 수 있게 한다. 클라우드 서비스를 사용할 때는 본인이 사용
Pod Readiness and Probes
object
Pod Readiness는 Pod가 트래픽을 처리할 준비가 되었는지를 나타내는 추가적인 지표이다. Pod Readiness는 외부에서 해당 Pod의 주소가 Endpoints 객체에 표시될지 여부를 결정한다. Deployment와 같이 Pod를 관리하는 Kubernetes 리소스들은 롤링 업데이트를 진행할 때 Pod Readiness를 고려하여 의사결정을 한다. 롤링 배포 중에 새 Pod가 Ready 상태가 되었지만 Service, NetworkPolicy, 또는 로드 밸런서가 아직 새 Pod를 받아들일 준비가 되지 않은 경우가 있다. 이로 인해 서비스 중단이나 백엔드 용량 손실이 발생할 수 있다. Pod spec에 아무 Probe도 정의되어 있지 않으면 Kubernetes는 세 가지 Probe 모두 성공으로
Pod
object
Pod는 동일한 실행환경에서 실행되는 애플리케이션 컨테이너와 볼륨으로 구성된 집합체다. 포드는 쿠버네티스 클러스터에서 배포 가능한 가장 작은 아티팩트(artipact)다. 즉, 포드에 있는 모든 컨테이너가 동일한 머신에 있음을 뜻한다. Pod에 있는 각 컨테이너는 각자의 cgroup을 운영하지만 몇가지 Linux 네임스페이스는 공유한다. Pod의 각 컨테이너는 각자의 cgroup 을 운영하지만 몇가지 리눅스 네임스페이스를 공유하며, 서로 다른 파드는 각 애플리케이션이 격리되어 있고 각기 다른 IP주소와 호스트네임을 갖는다. 또한 System V IPC나 POSIX 메시지 큐(IPC 네임스페이스)를 통해 기본 프로세스 간 통신 채널을 사용해 서로 통신할 수 있다. 동일한 노드에서 동작하는 서로 다른 Pod의
RollingUpdate
object
Rolling Update는 k8s의 업데이트 방법 중 하나로, 새로운 버전의 애플리케이션을 배포하고 기존 버전을 점진적으로 대체하는 과정으로 진행된다. 새로운 버전의 Pod로 트래픽이 전달되기 전까지 기존 버전이 유지되므로 무중단으로 애플리케이션을 업데이트 가능한 장점이 있다. 그러나 새로운 버전의 Pod와 기존 Pod가 함께 유지되는 기간이 존재하기 때문에 업데이트 중에 리소스를 더 사용할 수 있다. 기본적으로 Rolling Update는 다음과 같은 단계로 이뤄진다. 새로운 버전의 애플리케이션을 배포한다. 이때 기존 버전은 유지된 상태로 새로운 버전의 Pod가 함께 생성된다. 새로운 버전의 Pod가 정상적으로 동작하고, 준비 상태가 되면, 이전 버전의 Pod을 하나씩 종료한다. 이때 제거되는 Pod
Service와 port
object
쿠버네티스 환경에서 Service는 Pod들을 통해 실행되고 있는 애플리케이션을 네트워크에 노출(expose)시키는 가상의 컴포넌트다. 쿠버네티스 내부의 다양한 객체들이 애플리케이션과, 그리고 애플리케이션이 다른 외부의 애플리케이션이나 사용자와 연결될 수 있도록 도와주는 역할을 한다. 쿠버네티스에 Service가 있는 이유는, Pod들이 반영속적인 특성을 가지고 있기 때문이다. 쿠버네티스에서의 Pod는 무언가가 구동 중인 상태를 유지하기 위해 동원되는 일회성 자원으로 언제든 다른 노드로 옮겨지거나 삭제될 수 있다. 또한 Pod는 생성될 때마다 새로운 내부 IP를 받게 되므로, 이것만으로 클러스터 내/외부와의 통신을 계속 유지하기 어렵다. 따라서 쿠버네티스는 Pod가 외부와 통신할 수 있도록 클러스터 내부에서
ingress
object
인그레스(ingress)는 클러스터 내의 서비스에 대한 외부 접근을 관리하는 API 오브젝트이며, 일반적으로 HTTP를 관리한다. 인그레스는 부하 분산, SSL 종료, 명칭 기반의 가상 호스팅을 제공할 수 있다. 인그레스는 클러스터 외부에서 클러스터 내부 서비스로 HTTP와 HTTPS 경로를 노출한다. 트래픽 라우팅은 인그레스 리소스에 정의된 규칙에 의해 컨트롤된다. 인그레스는 외부에서 서비스로 접속이 가능한 URL, 로드 밸런스 트래픽, SSL / TLS 종료 그리고 이름-기반의 가상 호스팅을 제공하도록 구성할 수 있다. 인그레스 컨트롤러는 일반적으로 로드 밸런서를 사용해서 인그레스를 수행할 책임이 있으며, 트래픽을 처리하는데 도움이 되도록 에지 라우터 또는 추가 프런트 엔드를 구성할 수도 있다. 인그레
가상 IP와 서비스 프록시
개념
쿠버네티스 클러스터의 모든 노드는 kube-proxy를 실행한다. kube-proxy는 ExternalName 이외의 유형의 서비스에 대한 “가상 IP”의 역할을 한다. service를 조회했을때 나오는 cluster IP가 바로 k8s의 프록시로 만들어진 가상 IP이다. 이 IP는 k8s 내부에서만 접근할 수 있다. 쿠버네티스에서 가상 IP를 사용하는 이유 쿠버네티스가 프록시를 통해 가상 IP를 만드는 이유는, 실제 IP와 DNS를 사용하기 부적절하기 때문이다. k8s의 서비스 객체는 IP를 할당할 수 있는 기기가 아니고 잠시 생겼다가 사라질 수 있는 유한한 존재이다. 하지만 서비스를 식별하고 호출할 수 있는 무언가가 필요하기 때문에 그 방법으로서 프록시로 만든 가상 IP를 사용하는 것이다. ku
사이드카 패턴
개념
사이드카 패턴이란 쿠버네티스와 같이 컨테이너 오케스트레이션 툴에서 구성할 수 있는 컨테이너 배치 패턴으로, 마치 오토바이 옆에 붙어 있는 사이드카와 비슷한 형태이다. 장점 1. 기존 로직의 변경 없이 기능 추가 사이드카 컨테이너를 통해 기존의 로직은 그대로 놔둔체 새로운 기능을 덧붙일 수 있다. 예를 들어 기존 http 프로토콜에 대해서만 서비스를 하는 웹서버에 tls layer를 추가하고 싶은 경우, 메인 컨테이너인 기존의 legacy 웹서버는 그대로 놔둔체 사이드카 컨테이너를 통해 https 서비스를 클라이언트에게 제공할 수 있다. 2. 컨테이너 재사용성 사이드카 컨테이너를 단일한 기능을 하게 모듈화하면 다른 곳에서 재사용하기 수월해진다. 대부분의 app에서는 로깅, 실행 프로세스 정보 확인 등의 작업들
OIDC Authentication with Dex
auth
OIDC (Open ID Connect) 인증 방법은 OAuth2 위에서 동작하는 인증으로, Github이나 Google과 같이 서드 파티에서 부여받은 OAuth 권한을 통해 쿠버네티스의 인증을 수행한다. 기존에 사용하던 OAuth 인증 방법을 쿠버네티스에 그대로 가져온다고 생각하면 이해하기 쉽다. OIDC 인증 방법은 OAuth + JWT 토큰을 사용한다는 점에서 Webhook Token 인증 방법과 차이점을 갖는다. OAuth 토큰을 관리하기 위한 중간 서버를 구현한 Dex를 사용하여 OIDC 인증을 구현해보자. Dex Concept Dex는 서드 파티로부터 OAuth 인증 토큰을 가져와 관리하는 인증 도구이다. OAuth를 사용하기 위해 반드시 Dex를 써야 하는 것은 아니지만, Dex는 OAuth 서
Token Webhook with Guard
auth
Webhook 서버에 인증 데이터를 전달한 뒤, 클라이언트가 유효한지 인증하여 Third party에 권한을 부여하는 Webhook Token 인증 방법에 대해 알아보자. 사용자는 미리 인증 데이터를 발급받아 놓고, 사용자가 인증 데이터를 Bearer 헤더에 담아서 REST API 요청을 보내면 API 서버는 클라이언트가 유효한지를 검증하기 위해 Webhook 서버에 인증 데이터를 전달한다. Webhook 서버는 해당 데이터를 검사한 뒤, 인증 여부를 API 서버에 반환하는 간단한 방식으로 되어 있다 Token Webhook, OIDC 중 어느 방법을 선택하든지에 상관 없이 클라이언트는 HTTP의 Bearer 헤더에 인증 데이터를 담아서 보내기만 하면 된다. 클라이언트는 인증 방법이 무엇인지 알 필요가
k8s 클러스터 root CA를 통한 사용자 인증
auth
k8s는 기본적으로 root CA 인증서를 스스로 발급해 사용한다. 이 인증서를 이용하면 별도의 Third-party 연동 없이도 User와 Group을 사용할 수 있다. 단, 이 방법은 여러모로 한계점이 많기 때문에 가능하면 사용하지 않는 것이 좋다. 인증서가 유출되었을 때 revoke가 힘들기도 하고, 파일 단위로 인증 정보를 관리하는 것은 매우 비효율적이고 보안에 취약하기 때문이다. 따라서 k8s는 인증서 발급을 통한 사용자 인증은 극히 제한된 경우에만 사용하고 있다. 대표적으로는 관리자 권한을 가져야 하는 system:master 그룹의 인증 정보를 생성한다거나 (/etc/kubernetes/admin.conf), k8s의 핵심 컴포넌트에 인증서를 발급한다거나 할 때가 이에 해당한다. 우선, k8s는
datadog APM 기능 사용하기
datadog
서버에 datadog agent를 설치하면 CPU 점유율, Memory, Disk사용량 등의 중요한 성능 정보를 모니터링할 수 있다. 하지만 애플리케이션의 전반적인 LifeCycle에 대한 리포트 (ex: GC, JVM, I/O 등)를 바탕으로 에러나 병목현상에 더 빠르게 대응할 수 있도록 하고싶다면 Datadog APM을 연결해야한다. APM 이란? Application Performance Monitoring 의 약자로 구동 중인 애플리케이션의 대한 성능측정과 에러탐지 등, 전반적인 애플리케이션 라이프사이클의 정보를 수집해 모니터링할 수 있게 해준다. 보다 편리성을 위해서 다양하게 시각화한 Metrics, 그리고 API 테스트도 지원한다. 여러 대의 애플리케이션에 설치가 가능하며 이를 한꺼번에 같은 UI
datadog
datadog
💡 APM, log, Infrastructure를 통합적으로 모니터링·관리하는 클라우드 모니터링 솔루션 여러 클라우드 환경에 나뉘어있는 리소스들을 통합적으로 모니터링 가능하다. 클라우드의 상태를 지속적으로 감시하여 예기치 못한 상황과 오류를 대비, 대응할 수 있다. 장점 에러를 빠르게 확인하여 신속한 대응 가능 애플리케이션 정보(log, query 등) 축적하여 데이터 기반 개선 개발자, 운영팀, 비즈니스 유저간 긴밀한 협업 다양한 언어과 환경을 지원하기 때문에, 원하는 애플리케이션에 확장 가능 커스텀 대시보드 생성 가능 공식 문서가 친절함 단점 비용이 많이 든다. 기능이 많아서 실무에 도입하기 위해 사전 지식이 필요함. Datadog의 주요기능 Integrations 여러가지 서비
Elastic Search
elk
확장성이 뛰어난 오픈 소스 전체 텍스트 검색 및 분석 엔진 대량의 데이터를 신속하고 거의 실시간으로 저장, 검색 및 분석 일반적으로 복잡한 검색 기능과 요구 사항이 있는 응용 프로그램을 구동하는 기본 엔진 / 기술 핵심 개념 Near Realtime (NRT) Elastic Search는 거의 실시간 검색 플랫폼 문서를 색인할 때부터 검색 기능할 때까지 약간의 대기시간(일반적으로 1초)이 매우 짧음 클러스터(Cluster) 전체 데이터를 함께 보유하고 모든 노드에서 연합 인덱싱 및 검색 기능을 제공하는 하나 이상의 노드(서버) 모음 -노드의 그룹이라고 생각 클러스터는 기본적으로 elasticsearch 라는 고유한 이름으로 식별 이 이름은 노드가 이름으로 클러스터에 참여하도록 설정된 경우 노드가
ElasticSearch 검색 명령어
elk
Elasicsearch 검색 명령어 클러스터 상태 (Health) 클러스터가 어떻게 진행되고 있는지 기본적인 확인 클러스터 상태를 확인하기 위해 _cat API를 사용 curl를 사용하여 수행 가능 -노드 정보: GET /_cat/nodes?v 상태 정보 : GET /_cat/health?v Elasticsearch에서 _언더바가 붙은 것들이 API v는 상세하게 보여달라는 의미 녹색 : 모든 것이 정상 동작 노란색 : 모든 데이터를 사용 가능하지만 일부 복제본은 아직 할당되지 않음(클러스터는 완전히 동작) 빨간색 : 어떤 이유로든 일부 데이터를 사용 불가능(클러스터가 부분적으로만 동작) 데이터베이스(index)가 가진 데이터 확인하기 index는 일반 RDB에서의 DB 역할 모든 인덱스 항목을
Logstash
elk
Logstash는 실시간 파이프라인 기능을 가진 데이터 수집 엔진 오픈소스이다. Logstash는 서로 다른 소스의 데이터를 동적으로 통합하고 원하는 대상으로 데이터를 정규화 할 수 있는 능력을 가진다. 다양한 입력과 필터 및 출력 플러그인을 통해, 모든 유형의 이벤트를 보강하고 변환할 수 있으며, 많은 기본 코텍이 처리 과정을 단순화한다. 따라서 Logstash는 더 많은 양과 다양한 데이터를 활용하여 통찰력 있게 볼 수 있게 해 준다. Logtash 파이프라인 Logstash의 전체적인 파이프라인에는 INPUTS과 FILTERS, 그리고 OUTPUT이 있다. 이 중에서 2가지의 필수적인 요소는 INPUTS과 OUTPUTS이고, 파싱 여부에 따라 필터는 선택적으로 사용이 가능하다. Logstash.ym
prometheus storage
prometheus
Prometheus는 기본적으로 로컬 디스크 기반의 시계열 데이터베이스를 내장하고 있다. 구조 2시간 단위의 블록(block) 으로 샘플 데이터를 그룹화하여 저장한다. 각 블록은 디렉터리 하나로 구성되고, 아래와 같은 구조를 가진다. chunks/ 하위 디렉터리: 해당 시간 구간의 시계열 샘플 데이터 chunks 디렉터리 안의 데이터는 기본적으로 최대 512MB 크기의 segment 파일들로 구성된다. index: 메트릭 이름 및 라벨 → 시계열 매핑 정보를 담고 있음 meta.json: 블록의 메타데이터 tombstones: 삭제 요청된 시계열 정보를 별도로 기록 (바로 삭제하지 않음) WAL (Write-Ahead Log, 선기록 로그) 최신 샘플 데이터는 아직 블록으로 완전히 저장되지
리버스 프록시
nginx
클라이언트 요청을 대신 받아 내부 서버로 전달해주는 것을 리버스 프록시(Reverse Proxy)라고 한다. 리버스 프록시가 필요한 이유 로드 밸런싱 : Nginx는 클라이언트의 요청을 프록시 서버에 분산하기 위해 로드 밸런싱을 수행하여 성능, 확장성 및 신뢰성을 향상시킬 수 있다. 캐싱 : Nginx를 역방향 프록시로 사용하면 미리 렌더링된 버전의 페이지를 캐시하여 페이지 로드 시간을 단축할 수 있다. 서버의 응답에서 수신한 콘텐츠를 캐싱하고 이 콘텐츠를 사용하여 매번 동일한 콘텐츠를 프록시 서버에 연결할 필요 없이 클라이언트에 응답하는 방식으로 구현하는게 가능해진다. SSL 터미네이션 : Nginx는 클라이언트와의 연결에 대한 SSL endpoint 역할을 할 수 있다. 압축 : 프록시 서
Mortar
tools
Mortar는 Linux의 물리적 보안 구성 요소들을 연결하는 프레임워크다. Mortar 모델을 통해 디스크에서 사용되는 모든 것이 암호화되거나, 서명되거나, 해시된다. 평문 시크릿이 저장되는 유일한 위치는 TPM 모듈이다. TPM은 특정 부팅 상태를 효과적으로 화이트리스트하는 데 사용되며, Mortar는 변조되지 않은 시스템이 감지될 때만 키를 해제하도록 구성한다. 이 검증 및 잠금 해제 프로세스가 완전히 자동화되어 있어서, 정상적인 시스템은 사용자 개입 없이 완전히 재시작된다. 덕분에 전체 디스크 암호화가 최종 사용자에게 훨씬 편리해지고, 서버에서도 실용적으로 사용할 수 있게 된다. 동작 방식 기본 디스크에서는 2개의 파
데브옵스
devops
DevOps는 development와 operations가 합쳐진 단어이며, 소프트웨어 개발과 배포 프로세스를 자동화하고 통합하는 개발방법론, 철학이다. 팀 지원, 팀 간 커뮤니케이션 및 공동 작업, 기술 자동화를 강조한다. DevOps는 소프트웨어 제공 프로세스를 효율적으로 수행하는 것을 목표로 한다. 이를 위해 워크플로를 자동화하고 신속하게 피드백하여 프로젝트를 더 잘 제어할 수 있도록 하는 여러 방법을 사용한다. DevOps 문화 철학 DevOps에서는 개발과 운영이라는 두 팀간의 장벽을 없애 개발자의 생산성과 운영의 안정성을 모두 최적화한다. 두 팀은 자주 소통하고, 효율성을 높이고, 고객에게 제공하는 서비스의 품질을 향상하기 위해 최선을 다한다. 최종 고객의 요구와 자신이 어떻게 이러한 요구를 해
CRC
l1 network access layer
CRC는 네트워크 등을 통하여 데이터를 전송할 때 전송된 데이터에 오류가 있는지를 확인하기 위한 체크값을 결정하는 방식을 말한다. 송신측에서는 CRC값을 데이터에 붙인 코드워드를 전송하며, 수신측에서는 수신된 코드워드에서 CRC값을 이용하여 에러를 발견한다. 오류 제어를 위한 후진 오류 수정(BEC, Backward Error Correction) 방식 중 오류 검출 방식이다. CRC는 이진법 기반의 하드웨어에서 구현하기 쉽고, 데이터 전송 과정에서 발생하는 오류들을 검출하는 데 탁월하다. 하지만 CRC의 구조 때문에 의도적으로 주어진 CRC 값을 갖는 다른 데이터를 만들기가 쉽고, 따라서 데이터 무결성을 검사하는 데는 사용될 수 없다. 이런 용도로는 MD5 등의 함수들이 사용된다. 코
Ethernet과 TokenRing
l1 network access layer
📡 Ethernet 이더넷(Ethernet)이란 CSMA/CD라는 프로토콜을 사용해 네트워크에 연결된 각 기기들이 하나의 전송 매체를 통해 인터넷 망에 접속해 통신할 수 있도록 하는 네트워크 방식이다. CSMA/CD란 Carrier Sense Multiple Access / Collision Detection의 약자로, 다중 접속(콜리전)이 생겼을때 그것을 감지해 대기 후 재전송하는 것을 뜻한다. 즉, 네트워크 상의 데이터 신호들을 감지하다 두 개 이상의 PC가 서로 데이터를 보내다가 충돌이 발생하면 임의의 시간동안 기다린 후 다시 데이터를 보낸다. 따라서 CSMA/CD라는 프로토콜을 사용하는 이더넷이라는 네트워킹 방식은 네트워크상에 하나의 데이터만 오고 갈 수 있다는 특징이 있다. 과거에 쓰이던 Toke
L2 스위치와 STP
l1 network access layer
개요 스위치: 같은 네트워크 내에서 통신을 중재하는 L2 장비 이더넷을 구성하기 위해 사용되는 경우 이더넷 스위치라고도 불린다 패킷 경합을 없애서 여러 단말이 동시에 효율적으로 통신할 수 있게 함 구조가 간단하고 가격이 저렴함. 신뢰성과 성능이 높음. MAC 주소 테이블 여러 NIC와 포트로 연결됨 각 NIC의 MAC을 기억해놓고, 어느 호스트가 특정 MAC 주소와 연결하고 싶다 요청하면 연결해줌 허브는 한 포트로 신호가 들어오면 같은 신호를 다른 모든 포트로 전달함 반면 스위치는 플러딩할 때만 모든 포트로 전달하고, 나머지의 경우에는 정보를 MAC 주소 Table에 저장해서 필요한 포트에만 전달하기 때문에 속도가 더 빠름 동작 과정 Address learning:  이더넷 프레임이
MTU
l1 network access layer
데이터링크에서 하나의 프레임 또는 패킷에 담아 운반 가능한 최대 크기 MTU란 TCP/IP 네트워크 등과 같은 패킷 또는 프레임 기반의 네트워크에서 전송될 수 있는 최대 크기의 패킷 또는 프레임을 말한다. 한 번에 전송할 수 있는 최대 전송량(Byte)인 MTU 값은 매체에 따라 달라진다. Ethernet 환경이라면 MTU 기본값은 1500, FDDI 인 경우 4000, X.25는 576, Gigabit MTU는 9000 정도 등 매체 특성에 따라 한 번에 전송량이 결정된다. 상위 계층(즉, 물리적, 데이터링크, 네트워크, 인터넷, 애플리케이션 중 네트워크 계층 이상 계층을 말함)의 데이터(헤더 포함된 전체 사이즈)의 수용 가능한 최대 크기로도 생각할 수 있다. 따라서, 상위 계층 프로토콜(네트워크 계층
NIC
l1 network access layer
NIC(Network Interface Card, Controller)는 컴퓨터를 네트워크에 연결하기 위한 하드웨어 장치이다. NIC는 이더넷 또는 Wi-Fi와 같은 특정 물리 계층 및 데이터 링크 계층 표준을 사용하여 통신하는데 필요한 전자 회로를 구현한다. 동일한 LAN(local area network) 상의 컴퓨터 간의 통신 및 IP(Internet Protocol)와 같은 라우팅 가능한 프로토콜을 통한 대규모 네트워크 통신을 가능하게 한다. 또, 케이블을 사용하거나 무선으로 컴퓨터 네트워크를 통해 컴퓨터가 통신할 수 있게 해준다. L2 장비로서 네트워킹 매체에 대한 물리적 액세스를 제공하고, 고유하게 할당된 MAC 주소를 사용하여 하위 수준의 주소 지정 시스템을 제공한다. 역할
데이터링크 제어(DLC)
l1 network access layer
데이터 링크 제어(DLC, DataLink Control)는 두 인접한 노드간의 통신의 프레임 짜기, 오류검출 작업 절차를 포함하는 데이터링크층의 부계층이다. 프레임 짜기 데이터 링크 층은 비트들을 프레임으로 만들어서 각 프레임이 다른 프레임과 구분되도록 해야한다. 데이터링크층의 프레임 짜기(framing)는 송신자와 수진자의 주소를 추가하여 한 방신지에서 한 목적지로 가는 메시지를 구분한다. 목적지 주소를 패킷이 가야 할 곳을 규정한다. 송신자 주소는 수신자가 수신에 대해 확인응답하는 데 필요하다. 프레임 크기 프레임은 고정 길이나 가변 길이가 될 수 있다. 고정 길이 프레임 짜기(fixed-size-framing), 그렇지 않고 크기가 때에따라 바뀌는 방식을 가변 길이 프레임 짜기(variable-siz
매체 접근 제어(MAC)
l1 network access layer
공유 링크를 사용할 떄 링크에 접근하는 것을 조율하기 위한 데이터링크 계층의 다중 접근 프로토콜 동시에 각 노드가 링크에 대한 접근을 확보했다는 것을 확정하고, 충돌을 방지한다 크게 임의접근 방식, 제어 접근 방식, 채널화 방식으로 총 세가지가 있다. 임의 접근 방식 다수 노드가 공유 매체에서 프레임을 전송하기 위해 스케줄링 및 전송 순서 없이 충돌 감지 및 회피, 충돌 발생 시 재전송 하는 방식이다. (일단 보내고 생각) 각 노드는 다른 노드의 간섭을 받지 않고 공유 매체에 접근할 권한을 보유한다. ALOHA 타 노드와 무관하게 프레임 전송, 충돌 허용프레임 충돌 시 전송 실패 프레임 재전송취약시간: 충돌이 발생할 수 있는 시간pure ALOHA: 언제든지 전송slotted ALOHA: 타임슬롯
아날로그, 디지털 신호와 전송
l1 network access layer
아날로그 신호 정현파: 단순 아날로그 신호 최대진폭(전압), 주파수(Hz), 위상(시각 0시에 대한 위치) 세가지 특성으로 나타낼 수 있음 파장: 주기나 전파속도로 구함 복합신호: 여러개의 단순 정현파로 이뤄짐 대역폭: 복합 신호에 포함된 주파수의 범위 (최고 주파수와 최저 주파수의 차이) 디지털 신호: 한정된 준위를 가짐 bit rate: 대부분의 디지털 신호는 비주기적이어서 주기나 주파수를 이용할 수 없음 대신 1초 동안 전송된 비트의 수를 나타내는 비트율을 bps(Mbps)로 표현 비트 길이: 한 비트가 전송매체를 통해 차지하는 길이 (파장과 비슷) 디지털 신호의 전송 데이터 통신에선 비주기 디지털 신호를 주로 다룸 기저대역(베이스밴드): 디지털 신호를 아날로그로 바꾸지 않
CIDR
l2 internet layer
인터넷에 연결되는 모든 컴퓨터, 서버 및 최종 사용자 디바이스에는 IP 주소라는 고유한 번호가 연결되어 있으며, 디바이스는 이러한 IP 주소를 사용하여 서로 찾고 통신한다. 1990년대 초반까지 IP 주소는 클래스 기반 주소 지정 시스템을 사용하여 할당되었다. 주소의 전체 길이는 고정되었으며 네트워크 및 호스트 부분에 할당되는 비트 수도 고정되었다. 즉, A, B, C, D, E 등으로 나뉘던 Class는 CIDR가 나오기 전 사용했던 네트워크 구분 체계이다. CIDR가 나오면서 Class 체계보다 더 유연하게 IP주소를 여러 네트워크 영역으로 나눌 수 있게 되었다. 클래스 없는 주소 또는 Classless Inter-Domain Routing(CIDR) 주소는 가변 길이 서브넷 마스킹(VLS
IP 데이터그램과 단편화
l2 internet layer
IP 데이터그램은 아래와 같은 형태로 구성되어있다. VERS 4비트로 데이터그램의 IP 프로토콜 버전을 명시한다. 다른 버전의 IP는 다른 데이터그램 형식을 사용하기 때문에 라우터는 버전 번호를 확인하여 데이터그램의 나머지 부분을 어떻게 해석하는지 결정한다. HLEN IPv4 데이터그램은 헤더에 가변 길이의 옵션을 포함하기 때문에 4비트의 헤더 길이를 통해 IP 데이터그램에서 실제 페이로드가 시작하는 곳을 명시해준다. 대부분 IPv4 데이터그램은 옵션을 포함하지 않아서 데이터그램의 헤더는 20바이트가 통상적이다. SERVICE TYPE 서비스 타입 비트는 서로 다른 유형의 IP 데이터그램을 구별한다. TOTAL LENGTH 바이트로 계산한 IP 데이터그램(헤더와 데이터)의 전체
IP
l2 internet layer
IP는 송신 호스트와 수신 호스트가 네트워크에서 정보(패킷)를 주고받는 데 사용하는 정보 위주의 규약이다. OSI 네트워크 계층에서 호스트의 주소지정과 패킷 분할 및 조립 기능을 담당한다. IP에서는 컴퓨터 네트워크에서 장치들이 서로를 인식하고 통신을 하기 위해 IP주소를 배정한 후, 그 주소를 사용해 데이터를 전송할 대상을 특정한다. IP의 특징 비연결성 패킷을 받을 대상과 연결을 확립하여 데이터를 전송하지 않는다. 패킷을 받을 대상이 없거나, 서비스 불능 상태여도 패킷 전송 비신뢰성(unreliability) IP는 전송 흐름에 관여하지 않기 때문에 보낸 정보가 제대로 갔는지 보장하지 않는다. 전송 과정에서 패킷이 손상되거나 패킷의 순서가 바뀐 경우, 또는 패킷이 사라진 경우에도 그 에러를 검출하
IPSec
l2 internet layer
IPSec IP계층(네트워크 계층)을 안전하게 보호하기 위한 기법이다. 대부분의 네트워크 응용프로그램은 IP 계층을 사용하기 때문에 IP계층에서 동작하는 보안, 즉, 패킷에 대한 보안을 제공하는 IP Security(IPSec)가 필요하다. 모드 IPSec에는 두 가지 모드가 있는데, IP의 내용(payload)만을 보호하느냐, 아니면 헤더까지 모두 보호하느냐에 따라서 전송 모드(Transport Mode), 후자는 터널 모드(Tunnel Model)로 나뉜다. 전송 모드(Transport Mode) 전송모드는 전송 계층와 네트워크 계층 사이에 전달되는 payload를 보호한다. 중간에 IPSec 계층이 있기 때문에 IPSec 헤더가 붙고, 이후에 네트워크 계층에서는 이것이 모두 상위층에서 보낸 데이터(pa
NAT
l2 internet layer
2011년 2월, 인터넷 주소 관리기구인 IANA는 더 이상의 IPv4 할당이 없을 것이라고 선언했다. IPv4는 약 43억 개의 한정된 주소를 사용할 수 있는데 반해 인터넷의 수요가 빠르게 증가하여 각 대륙에 할당한 IPv4가 동이 나버려 더 이상 할당할 수 없게 된 것이다. IPv6가 조금씩 상용화 되고 있긴 하지만, 이상하게도 우린 아직도 IPv4를 원활하게 사용하고 있다. 많지 않은 수의 IPv4로 현재까지 별 탈 없이 인터넷을 사용할 수 있게 된 것은 Private Network(이하 사설망) 덕분이라고 볼 수 있다. Private Network(사설망)의 탄생 사설망 또는 프라이빗 네트워크(private network)는 인터넷 어드레싱 아키텍처에서 사설 IP 주소 공간을 이용하는 네트워크이며
secondary IP
l2 internet layer
Secondary IP란 현재 서브넷에 의해 나뉘어져있는 네트워크 대역에 추가적인 호스트가 필요할때 전체적인 구성을 변경하지 않고도 확장이 가능하게 하는 기술이다. 예를 들어 10.0.0.0/24 의 네트워크 인터페이스를 가진 라우터내의 호스트가 200명이 있고 갑작스럽게 추가적으로 200명의 호스트가 더 필요해졌을때 해당 네트워크 인터페이스에 10.0.1.0/24 라는 Secondary IP 대역을 부여하면 10.0.1.0/24 대역까지 같은 네트워크 대역으로 인식시킬 수 있다. 장점 가용성(내결함성 향상) Host의 입장에서 10.0.0.0/24대의 NIC 한 개와 10.0.1.0/24대의 NIC 한 개를 달고 있을 때 하나의 네트워크 카드가 망가지더라도 다른 네트워크 카드로 통신이 가
라우터
라우터
라우터는 경로를 지정해주는 장비이다. 들어오는 패킷의 목적지 IP 주소를 확인하고 자신이 가진 경로(Route) 정보를 이용해 패킷을 최적의 경로로 포워딩한다. Hop-by-Hop 라우팅: 라우터는 인접한 라우터까지만 경로를 지정하면 인접 라우터(Next-hop)에서 최적의 경로를 다시 파악한 후 라우터로 패킷을 포워딩한다. Next-hop을 지정할 때는 세 가지의 방법을 사용할 수 있다. 다음 라우터의 IP을 지정 라우터의 나가는 인터페이스를 지정 : 상대방 넥스트 홉 라우터의 IP주소를 몰라도 MAC주소 정보를 알아낼 수 있을 때만 사용. 라우터의 나가는 인터페이스와 다음 라우터의 IP를 동시에 지정 : 이 경우 VLAN 인터페이스와 같은 논리적인 인터페이스를 사용할 수 있다.
멀티캐스트 라우팅
라우터
유니캐스팅: 하나의 발신지와 목적지(1:1) 멀티캐스팅: 하나의 발신지와 목적지 그롬(1:n ) DVMRP(Distance Vector Multicast Routing Protocol) 거리-벡터 멀티캐스트 라우팅 프로토콜 유니캐스트 라우팅에 사용되는 RIP를 기반으로 멀티캐스팅이 가능하도록 확장한 것이다. DVMRP는 발신지 기반 트리 기법을 사용한다. 멀티캐스트 패킷을 수신할 각 라우터는 먼저 다음과 같은 세 가지 단계를 거쳐 발신지 기반 멀티캐스트 트리를 생성해야 한다. 라우터는 RPF(Reverse Path Forwarding)로 발신지와 자신 사이의 최적 트리를 생성하는 시뮬레이션을 한다. Multicast에서 모든 노드에 대한 최적 트리를 찾기는 복잡하다. 대신, 각 하위 노드에서
서브넷
l2 internet layer
흔히 사용되는 IPv4 주소 체계는 클래스를 나누어 IP를 할당한다. 하지만 이 방식은 매우 비효율적이다. 예를 들어 어떤 기관에 A 클래스를 할당한다고 하면 16,777,214개의 호스트를 할당할 수 있게 되는데, 이 기관이 100개의 호스트를 할당할 때 16,777,114개의 호스트는 그대로 낭비된다. 이러한 비효율성을 해결하기 위해 네트워크 장치들의 수에 따라 효율적으로 사용할 수 있는 서브넷(subnet)이 등장하게 되었다. 서브넷은 IP 주소에서 네트워크 영역을 부분적으로 나눈 부분 네트워크를 뜻한다. 이러한 서브넷을 만들 때 사용되는 것이 바로 서브넷 마스크이다. 즉, 서브넷 마스크는 IP 주소 체계의 Network ID와 Host ID를 분리하는 역할을 한다. 서브넷 마스
4계층 장비
l3 transport layer
4계층 장비는 TCP와 같이 4계층 헤더에 있는 정보를 기반으로 동작한다. 4계층 이상에서 동작하는 로드 밸런서, 방화벽과 같은 장비를 세션 장비라 부른다. 세션 장비에서 고려해야할 요소는 다음과 같다. 세션 테이블 세션 장비는 세션 테이블 기반으로 운영된다. 세션 정보를 저장, 확인하는 작업 전반을 이해해야 한다. 세션 정보는 세션 테이블에 남아 있는 라이프타임이 존재한다. Symmetric(대칭)경로 요구 Inbound와 Outbound 경로가 일치해야 한다. 세션 동기화 또는 터널링(경로 보정)을 통해 해결할 수 있다. 정보 변경(로드 밸런서의 경우) IP주소가 변경되며 확장된 1.7 로드 밸런서(ADC)는 애플리케이션 프로토콜 정보도 변경된다.
Sticky Session과 Session Clustering
l3 transport layer
Load balancing이란 대용량 트래픽을 장애 없이 처리하기 위해 여러 대의 서버에 적절히 트래픽을 분배하는 것이다. 이러한 서비스에서는 세션 관리에 문제가 생길 수 있다. 예를 들어, 로그인 정보를 한 서버의 세션에 저장했는데 다음 요청을 다른 서버에 보내는 경우에 로그인 정보가 사라지는 문제가 생긴다. 이러한 문제를 해결하기 위해 특정 클라이언트의 요청을 처음 처리한 서버로만 보내는 것을 Sticky Session이라 말한다. 일반적으로 특정 서버로 요청 처리를 고정시키는 방법은 Cookie를 사용하거나 클라이언트의 IP tracking 하는 방식이 있다. AWS ELB는 cookie를 사용하여 Http Response에 cookie를 이용해서 해당 클라이언트가 가야하는 EC2 instance의 정
TCP와 UDP
l3 transport layer
TCP는 네트워크 계층 중 전송 계층에서 사용하는 프로토콜로서, 장치들 사이에 논리적인 접속을 성립(establish)하기 위하여 연결을 설정하여 신뢰성을 보장하는 연결지향적 프로토콜이다. TCP는 흐름제어, 혼잡제어 등을 통해 네트워크에 연결된 컴퓨터에서 실행되는 프로그램 간에 일련의 옥텟(데이터, 메세지, 세그먼트라는 블록 단위)을 안정적으로, 순서대로, 에러없이 교환할 수 있게 한다. TCP의 특징 연결지향 TCP는 통신 과정에서 클라이언트와 서버간에 3-way handshaking으르 통해 연결을 확립한 후에 전송을 시작하기 때문에 두 호스트가 논리적으로 연결되어있음을 보장할 수 있다. 흐름제어(Flow control) 흐름제어는 송신측과 수신측의 데이터 처리 속도 차이를 해결하기 위한 흐름제어
CDN
l4 appplication layer
CDN은 지리적으로 분산된 여러 개의 서버이다. 네트워크 설계로 인해 발생하는 통신 대기, 지연시간을 줄이는 것을 목적으로 한다. CDN은 사용자가 전세계에 있더라도 가까운 CDN 서버에 요청을 보내 빠르게 응답을 받을 수 있고, 한 서버에 장애가 생겼을떄 다른 서버를 사용하여 서비스를 그대로 응답받을 수도록 한다. 또한, 클라이언트와 웹 사이트 서버 간에 중간 서버를 두어 효율성을 높이고, 클라이언트-서버 통신의 일부를 관리한다. 웹 서버에 대한 웹 트래픽을 줄이고, 대역폭 소비를 줄이며, 애플리케이션의 사용자 환경을 개선한다. 장점 페이지 로드 시간 단축 페이지 로드 시간이 너무 느리면 웹 사이트 트래픽이 감소할 수 있다. CDN은 반송률을 줄이고 사용자가 사이트에서 보내는 시간을 늘릴 수 있다.
FTP Active, Passive mode
l4 appplication layer
FTP는 파일을 전송하기 위해 두 개의 세션을 사용한다. 컨트롤 프로토콜과 데이터 프로토콜이 완전히 분리되어있고, 통신 방법이 다른 두가지 모드를 가지고 있다. Active 모드 FTP의 기본적인 구동 방식은 Active 모드이다. 컨트롤 프로토콜을 클라이언트에서 서버로 통신을 시작하고, 데이터 프로토콜은 서버에서 클라이언트 쪽으로 데이터를 푸시하는 방식이다. Active 모드의 작동 흐름은 다음과 같다. 클라이언트가 FTP 서버에 접속. 클라이언트는 1023번 이상의 TCP 포트를, 서버는 21번 포트 사용 클라이언트가 1025번 포트로 데이터를 수신하겠다 알림 서버는 송신하겠다고 응답 서버에서 데이터를 보냄 Active 모드를 사용할 때 중간에 방화벽이나 세션 장비가 있으면 동작 방식에 맞춰 반댓
SMTP의 보안 시스템
l4 appplication layer
SMTP는 MARC, DKIM, SPF 등 세 가지 방법으로 이메일에 대한 보안을 지킨다. 함께 사용하면 스팸 발송자, 피싱 공격자 등 권한이 없는 당사자가 소유하지 않은 도메인을 대신하여 이메일을 보내는 것을 막을 수 있다. SPF, DKIM, DMARC를 올바르게 설정하지 않은 도메인에서는 이메일이 스팸으로 격리되거나 수신자에게 전달되지 않을 수 있다. 또한 스팸 발송자가 자신을 사칭할 위험도 있다. DKIM, SPF, DMARC 레코드는 모두 DNS TXT 레코드로 저장된다. 1. SPF (Sender Policy Framework) SPF는 누군가(google.com)로부터 메일이 발송되었을 때, 이 메일의 발송지(111.111.111.111)가 진짜 해당 도메인인 google.co
HTTP
http
HTTP는 웹 상에서 하이퍼텍스트 등의 정보를 주고받는 데 쓰이는 프로토콜로, 서버와 클라이언트의 사이에서 어떻게 메시지를 교환할지를 정해 놓은 규칙이다. HTTP는 요청(Request)와 응답(Response)로 구성되어 있고, 클라이언트가 요청을 하면 서버가 응답을 하는 구조로 되어 있다. HTTP 메서드 GET 리소스를 조회하는 메서드이다. 서버에 전달하고 싶은 데이터는 query(쿼리스트링)를 통해 전달할 수 있다. 캐싱이 가능하다. POST 요청한 데이터를 처리하는 메서드이다. 메시지 바디를 통해 서버로 요청 데이터 전달한다. (들어온 데이터를 처리하는 모든 기능을 수행할 수 있다.) 대상 리소스가 가지는 의미에 따라 요청에 포함된 표현을 자유롭게 처리하도록 요청한다. 리소스를 생성하는
OSI 7Layer
network
OSI 모형은 국제표준화기구(ISO)에서 개발한 모델로, 컴퓨터 네트워크 프로토콜 디자인과 통신을 계층으로 나누어 설명한 것이다. 일반적으로 OSI 7 계층(OSI 7 Layer)이라고 한다. 분산된 이기종 시스템간의 네트워크 상호호환을 위한 표준 아키텍처를 정의하여, 통신을 하기 위한 업무를 계층별로 분할하고 분업할 수 있다는 점에서 의의를 가진다. 계층 기능 1. 물리 계층(Physical Layer) 네트워크 데이터가 전송되기 위한 기본적인 하드웨어 기술을 담당한다. 다양한 특징의 하드웨어 기술이 접목되어 있기에 OSI 아키텍처에서 가장 복잡한 계층으로 간주된다. 리피터, 네트워크 허브, 모뎀 등의 장비가 물리계층에 속하며 비트단위의 데이터를 다룬다. 2. 데이터 링크 계층(Date Link L
Switch
network
네트워크 스위치는 받은 패킷을 어느쪽으로 보낼지 결정하는 역할을 하는 하드웨어이다. 스위치는 어떤 정보를 기준으로 스위칭을 하느냐에 따라 L1, L2, L3, L4, L7 스위치 등 다양한 종류가 있다. L1 허브를 L1 스위치라고 부르기도 한다. L2 L2 스위치는 스위치 패킷이 왔을 때, 그 패킷의 목적지가 어디인지를 본 후에 해당 목적지로 보내주는 역할을 수행한다. 2계층 주소인 MAC 주소를 기반으로 스위칭한다. 허브가 한 포트로 신호가 들어오면 같은 신호를 다른 모든 포트로 전달하는 것에 비해서, 스위치는 신호를 필요로 하는 포트에만 신호를 전달하기 때문에 속도가 빠르다. 스위치가 이 기능을 수행하기 위해서는 지나가는 트래픽의 목적지를 정확히 알아야 하니, 자신과 연결된 장비들의 맥 주소와 그 장비
가상화 기술
개념
가상화는 컴퓨터에서 컴퓨터 리소스의 추상화를 일컫는 광범위한 용어이다. “물리적인 컴퓨터 리소스의 특징을 다른 시스템, 응용 프로그램, 최종 사용자들이 리소스와 상호 작용하는 방식으로부터 감추는 기술”로 정의할 수 있다. 이것은 다중 논리 리소스로서의 기능을 하는 것처럼 보이는 서버, 운영 체제, 응용 프로그램, 또는 저장 장치와 같은 하나의 단일 물리 리소스를 만들어 낸다. 아니면 단일 논리 리소스처럼 보이는 저장 장치나 서버와 같은 여러 개의 물리적 리소스를 만들어 낼 수 있다. 출처: 위키백과 네트워크에서는 다양한 가상화 기술이 사용되고 있다. 가상화 기술을 이용하면 리소스를 더 효율적으로 사용할 수 있고 운영 비용이나 도입 비용을 줄일 수 있다. 기존 레거시 환경의 문제점을 해결할 수도
네트워크 보안
개념
정보 보안 IT에서 다루는 정보 보안은 “다양한 위협으로부터 보안을 보호하는 것”을 뜻한다. 3대 보안 정의는 다음과 같다. 기밀성(Confidentiality) 인가되지 않은 사용자가 정보를 보지 못하게 하는 작업이다. 대표적인 기밀성은 암호화 작업이다. 무결성(Integriality) 정확하고 완전한 정보 유지에 필요한 모든 작업을 말한다. 누군가가 정보를 고의로 훼손하거나 중간에 특정 이유로 변경이 가해졌을 때, 그것을 파악해 잘못된 정보가 전달되거나 유지되지 못하게 하는 것이 무결성이다. IT의 대표적인 무결성 기술은 MD5, SHA와 같은 Hash 함수를 이용해 변경 여부를 파악하는 것이다. 가용성(Availability) 정보가 필요할 때, 접근을 허락하는 일련의 작업이다. 우리가
네트워크 침해
개념
스니핑 한 서브 네트워크 내에서 전송되는 패킷의 내용을 임의로 확인하는 공격 중요한 데이터는 SSL와 같은 암호화 통신 방식을 사용함으로써 대응한다. 스푸핑 네트워크 서비스 혹은 패킷 정보를 임의로 변경하여 공격에 사용하는 기법 IP 주소, DNS 주소, MAC 주소 등의 정보를 변조하여 공격의 탐지 및 역추적이 어렵다. IP 스푸핑 TCP/IP 구조의 취약점을 악용, 공격자가 자신의 IP를 변조해 IP 기반 인증 등의 서비스를 무력화한다. IP 기반 인증을 최소화하고 TCP 시퀀스 번호를 랜덤으로 지정해 대응한다. ARP 스푸핑 ARP 프로토콜의 취약점을 이용, IP-MAC 매핑 정보를 브로드캐스트해 ARP 테이블의 정보를 변조한다. arp -s ip mac 명령어로 정적 ARP 매핑을 등록한다.
네트워크
개념
네트워크 네트워크: 서로 다른 컴퓨터끼리 데이터 주고 받기 프로토콜: 네트워크 통신을 하기 위한 규칙 데이터를 주는 사람과 받는 사람은 서로 약속해놓은 방식(프로토콜)으로 통신 MAC: 기기 주소 (장치별로 다 다름, 장비 식별용) IP: 어느 네트워크의 어느 컴퓨터인지를 식별하는 주소 네트워크 번호(Network Part)와 컴퓨터 번호(Host Part)를 조합하여 만들어짐 네트워크가 바뀌면 IP도 바뀌기 때문에 동적이다 MAC이 고유한 주소면 IP를 또 사용할 필요가 없는 것 아닌가? IP는 라우팅 하기에 적합하게 설계된 형태로, 주로 Area code를 포함하고 있음 ex) 만약에 편지를 주소가 아닌 주민등록번호로 보낸다면 어떻게 될까? ARP: 보통 network 통신에서는 IP를 목적지로
이중화
개념
이중화의 목적 장애가 발생하더라도, 이중화 된 다른 인프라를 통해서 서비스가 지속되도록 해준다. (SPoF 방지) 액티브-스탠바이가 아닌, 액티브-액티브로 구성할 때는, 이중화 된 인프라에서 서비스 요청을 동시에 처리할 수 있기에, 처리 가능 용량이 늘어난다. 다만, 이렇게 증가된 인프라를 기준으로 서비스를 운영하다보면, 특정 지점에 장애가 발생했을 때 인프라 용량이 절반으로 떨어져 정상적인 서비스 운영이 어렵다. 따라서 인프라 이중화를 구성할 때는, 이중화 된 인프라 중 일부에서 장애가 발생하더라도 정상적인 서비스에 문제가 없도록 용량을 산정해 설계해야 한다. LACP 두 개의 물리 인터페이스가 논리 인터페이스를 구성하는 프로토콜 1990 년대 중반까지는 각 벤더별로 장비 간 대역폭을 늘리기 위
로드밸런서
network
부하 분산 서비스 규모가 커질 때, 물리, 가상 서버 한 대로는 모든 서비스를 수용할 수 없게 된다. 서비스 가용성을 높이기 위해서 보통 하나의 서비스를 두 대 이상의 서버로 구성하는데, 각 서버 IP 주소가 다르기 때문에 사용자가 서비스를 호출할 때는 어떤 IP 로 서비스를 요청할 지 결정해야 한다. 이런 문제점 해결을 위해서, L4, L7 로드밸런서를 사용한다. 로드 밸런서는 부하를 다수의 장비에 분산시키기 위해 가상 IP 주소를 갖게 된다. 사용자가 VIP 로 서비스를 요청하게 되면, 해당 VIP에 연결된 실제 서버의 IP로 해당 요청을 전달한다. 헬스 체크 로드 밸런서에서는 주기적으로 부하 분산을 하는 각 서버의 서비스를 주기적으로 헬스 체크해 정상적인 서비스로만 트래픽이
브라우저에 url을 입력하면 어떤일이 생길까?
network
📡 브라우저에 url을 입력하면 어떤일이 벌어질까? 1. 브라우저 주소창에 google.com을 입력한다. 2. 웹 브라우저가 도메인의 IP 주소를 조회한다. DNS(Domain Name System)는 웹 사이트의 이름(URL)을 가지고 있는 데이터베이스와 같다. 인터넷의 모든 URL에는 고유한 IP 주소가 할당되어 있으며, IP 주소는 액세스 요청 웹 사이트의 서버를 호스트하는 컴퓨터에 속한다. DNS는 영어로된 URL과 IP를 연결해주는 시스템이다. 예를 들어, www.google.com의 IP주소는 http://209.85.227.104이다. 따라서 원하는 경우 브라우저에서 를 입력해도 www.google.com에 접속할 수 있다. nslook
VMware Fusion Ubuntu 디스크 용량 늘리기
vm
VMWare + Ubuntu 조합을 사용하다 보면, 미리 설정해 둔 디스크 용량이 부족한 경우가 있다. VMware의 옵션으로 디스크 용량을 늘릴 수는 있지만, 이 경우 소프트웨어적으로 인식을 못하기 때문에 직접 우분투에서 설정을 변경해야 한다. VMWare 디스크 할당 늘리기 우선 가상 머신을 Shut down 시킨 후 설정에 들어가서 하드디스크 용량을 늘려준다. 디스크 파티션 늘리기 lsblk 명령어로 디스크를 확인해보면 nvme0n1이라는 디스크의 용량이 늘어나있는 걸 볼 수 있다. 해당 디스크의 파티션 중 1, 2번 파티션은 부팅을 위한 공간이고, 3번 파티션이 실제 lv 볼륨을 가지고 있는 파티션이다. 따라서 growpart 명령어로 /dev/nvm0n1의 3번 파티션에 공간을 더 할당해준다
c언어 컴파일과정
os
1) 전처리 code.c -code.i : 전처리기(Preprocessor)로 컴파일 전에 코드를 적정한 상태로 준비하거나 처리하는 일 include &x3C;stdio.h>define STD 10define STD 10"> 전처리기는 필요한 헤더파일을 불러오거나, 기호 상수를 정의해서 코드 상으로 필요한 내용을 먼저 채워주는 역할을 한다. 전처리기는 include 구문을 만나면 해당하는 헤더 파일을 찾아 그 내용을 순차적으로 삽입한다. 그리고 define 부분을 심볼 테이블에 저장하고, 심볼 테이블에 들어 있는 문자열과 같은 내용을 만나면 해당 내용으로 치환한다. (매크로 치환 작업. ifdef 와 같은 전처리기 구문도 처리됨) 2) 컴파일 code.i -code.s : 컴파일러(Compi
사용자 관리
authority
root 계정의 UID 값은 0이다. root 이외에 UID가 0인 사용자가 없도록 해야 한다. TMOUT 환경 변수를 사용해 일정시간 미사용시 자동으로 로그아웃 되도록 설정하여 보안을 강화할 수 있다. 사용자 인증 모듈인 PAM을 이용해 root 계정으로의 직접 로그인을 차단할 수 있다. 일반 사용자에게 특정 명령어에 대한 root 권한이 필요할 때는 su 명령어보다는 sudo 명령어를 이용하도록 한다. 계정 관리 계정 정보가 저장되어있는 디렉토리에 대해 알아보자. /etc/passwd 비밀번호를 파일 내 계정 정보와 함께 저장하는 일반 정책에서 사용된다. passwd 파일의 로그인 쉘을 점검하여 로그인이 불필요한 계정에 대한 접근권한을 설정해야 한다. [user_account]:
LVM
disk & dir
LVM이란 Logical Volume을 효율적이고 유연하게 관리하기 위한 커널의 한 부분이자 프로그램이다. 기존방식이 파일시스템을 블록 장치에 직접 접근해서 R/W를 했다면, LVM은 파일시스템이 LVM이 만든 가상의 블록 장치에 R/W를 하게 된다. 이처럼 LVM은 물리적 스토리지 이상의 추상적 레이어를 생성해서 논리적 스토리지(가상의 블록 장치)를 생성할 수 있게 한다. 직접 물리 스토리지를 사용하는 것보다 다양한 측면에서 유연성을 제공하기 위해, 유연한 용량 조절, 크기 조정이 가능한 스토리지 풀(Pool), 편의에 따른 장치 이름 지정, 디스크 스트라이핑, 미러 볼륨 등 기능을 가지고 있다. LVM의 주요 용어를 알아보자. PV(Physical Volume) LVM에서 블록 장치(블록 단위로 접근하는
Linux 디렉토리 구조
disk & dir
/bin: 기본 명령어 저장 /sbin: 시스템 관리를 위한 명령어들이 저장 /etc: 환경설정에 연관된 파일들과 디렉터리들이 저장 2016(1) /etc/rc.d: 시스템의 부팅과 런 레벨 관련 스크립트들이 저장 /etc/inittab: init을 설정하는 파일 /etc/issue: 로그인을 위한 프롬프트가 뜨기 전에 출력되는 메시지를 설정하는 파일 /etc/issue.net: issue 파일과 기능은 같으나, 원격지 상에서 접속(telnet 등)할 경우에 출력되는 메시지 설정 /etc/motd: 로그인 성공 후 쉘이 뜨기 전에 출력되는 메시지를 설정하는 파일 /etc/nologin.txt: 사용자의 쉘이 /sbin/nologin으로 지정되어 있을 때, 로그인 거부 메시지를 설정하는 파일 •
RAID
disk & dir
RAID(Redundant Array of Independent Disks) 직역하면 복수 배열 저가/독립 디스크이다. 저장장치 여러 개를 묶어 고용량, 고성능인 저장 장치 한 개와 같은 효과를 얻기 위해 개발된 기법이다. RAID의 주 사용 목적은 크게 가용성과 고성능 구현으로 구분된다. 동작 방식에 따라 Level 0~6으로 분류한다. 주로 사용되는 것은 0, 1, 5, 6이며 무정지 구현을 극도로 추구하면 RAID 1, 고성능 구현을 극도로 추구하면 RAID 0, RAID 5, 6은 둘 사이에서 적당히 타협한 형태이다.. RAID 10이나 RAID 01과 같이 두 가지 방식을 혼용하는 경우도 있다. RAID 0: 스트라이핑 기능(분배 기록) 사용 여러 개의 멤버 하드디스크를 병렬로 배치하여 거대한
백업
disk & dir
Day-zero Backup: 시스템을 설치한 후 사용자들이 시스템을 사용하기 전에 시스템을 백업하는 것 Full Backup: 주기적으로 시스템을 백업하는 것 Incremental Backup: 특정한 이벤트 후 또는 주기적으로 이전의 백업 후 변경된 파일들만 백업 하는 것 단순 백업: 첫 백업 때 풀 백업을 진행한 후, 그 다음부터 변경분 백업을 수행하는 것 다단계 백업(Multilevel Backup): 큰 규모나 중요한 시스템의 백업을 수행하는 것 디렉터리 단위 백업 명령어 tar 마운트된 파일시스템 내에서 백업 [-g]: 증분 백업을 위한 옵션 cpio 많은 양의 데이터를 테이프 드라이브에 백업하기 위한 명령어 네트워크를 통한 백업 / 증분 백업을 지원하지 않는다. 주요 옵션 [-c]
파일 시스템
disk & dir
ext 리눅스 초기에 사용되던 파일 시스템 ext2 ext3가 개발되기 이전까지 가장 많이 사용하는 파일 시스템으로 리눅스 파일 시스템 대부분의 기능을 제공하는 파일 시스템이다. ext2는 뛰어난 안정성과 속도로 가장 유명한 파일 시스템으로 자리잡았고 ext3 또한 ext2에 기반해서 개발되었다. 또한 쉽게 호환되며 업그레이드도 어렵지 않게 설계되어 있다. ext3 ext2에서 fsck의 단점을 보완하기 위해 저널링 기술을 도입한 파일시스템 저널링(Journaling) 기술: 데이터를 디스크에 쓰기 전에 로그에 데이터를 남겨 fsck보다 빠르고 안정적인 복구 기능을 제공 최대 볼륨크기 2TB~16TB 최대 파일크기 16GB~2TB 지원 하위 디렉터리 수 :32000개 ext4 ex
파일 종류
disk & dir
파일 형태로 표현된 커널 내 객체, 즉 OS의 자원이다. 유닉스 시스템은 OS 자원을 파일 형태로 표현한다. OS 자원이라고 함은 디스크, CPU, 네트워크, RAM 등을 말한다. 리눅스에서 이런 자원에 데이터 전송, 장치 접근 시 사용하는 파일을 특수 파일이라고 한다 device files, pipes, socket, ... 특수 파일은 장치와 데이터를 주고 받는 통로이다 데이터 블록이 없으며(디스크에 저장 X) 장치 번호를 inode에 저장한다. 모니터나 프린터 역시 특수 파일을 통해 데이터를 주고 받는다. 디바이스는 반드시 HW를 말하는것이 아니고 SW적인 디바이스도 있다. 파일 종류 문자 : 일반 파일d : 디렉토리b : 블록 장치 특수 파일c : 문자 장치 특수 파일l : 심볼릭 링크 device
디버깅
kernel
커널 디버깅에는 세 가지 요소가 필요하다. 버그가 처음 등장한 커널 버전을 파악할 수 있는가? 버그를 재현할 수 있는가? 커널 코드에 관한 지식을 갖추고 있는가? 버그를 명확하게 정의하고 안정적으로 재현할 수 있다면 성공적인 디버깅에 절반 이상 달성한 것이다. ​ 출력을 이용한 디버깅 printk()와 웁스(oops) 커널 출력 함수인 printk()는 C 라이브러리의 printf() 함수와 거의 동일하다. 주요 차이점은 로그수준(Loglevel)을 지정할 수 있다는 점이다. 가장 낮은 수준인 KERN_DEBUG 부터 가장 높은 수준인 KERN_EMERG 까지 7단계로 설정할 수 있다. printk()의 장점은 커널의 어느 곳에서도 언제든지 호출할 수 있다는 점이다. 인터럽트 컨텍스트, 프
메모리 관리와 캐시
kernel
1. 페이지 (Page) &x26; 구역 (Zone) 프로세서가 메모리에 접근할 때 가장 작은 단위는 byte 또는 word지만, MMU와 커널은 메모리 관리를 페이지 단위로 처리한다. 페이지 크기는 아키텍처 별로 다르며 보통 32-bit 시스템에선 4KB, 64-bit 시스템에선 8KB다. 커널은 하나의 페이지를 여러 구역(zone)으로 나눠 관리한다. (&x3C;linux/mmzone.h>에 정의) ZONE_DMA: DMA를 수행할 수 있는 메모리 구역 ZONE_DMA32: 32-bit 장치들만 DMA를 수행할 수 있는 메모리 구역 ZONE_NORMAL: 통상적인 페이지가 할당되는 메모리 구역 ZONE_HIGHMEM: 커널 주소 공간에 포함되지 않는 ‘상위 메모리’ 구역 메모리 구역의 실제 사용
모듈과 장치 관리
kernel
1. 정의 모듈: 커널 관련 하위 함수, 데이터, 바이너리 이미지를 포함해 동적으로 불러 올 수 있는 커널 객체를 의미한다. 장치: 리눅스 커널은 장치를 블록 장치, 캐릭터 장치, 네트워크 장치 3가지로 분류한다. 모든 장치 드라이버가 물리장치를 표현하는 것은 아니며 커널 난수 생성기, 메모리 장치처럼 가상 장치도 표현한다. 2. 모듈 사용하기 모듈 만들기 모듈 개발은 새로운 프로그램을 짜는 것과 비슷하다. 각 모듈은 소스파일 내에 자신의 시작위치(module_init())와 종료위치(module_exit())가 있다. 아래는 ‘hello, world’를 출력하는 간단한 모듈의 코드이다. include &x3C;linux/init.h>include &x3C;linux/module.h>inclu
시스템 콜과 인터럽트
kernel
커널은 시스템콜의 일관성, 유연성, 이식성​ 3가지를 확보하는 것을 최우선 사항으로 생각하고 있다. 따라서 커널은 POSIX 표준에 따라 표준 C 라이브러리 형태로 시스템콜을 제공한다. 리눅스 커널에서 시스템콜은 네 가지 역할을 수행한다. 사용자 공간에 HW 인터페이스를 추상화된 형태로 제공한다. 시스템에 보안성 및 안정성을 제공한다. 인터럽트(및 트랩)와 함께 커널에 접근할 수 있는 유일한 수단이다. 사용자 공간과 기타 공간을 분리해 프로세스별 가상환경(가상메모리, 멀티태스킹 등)을 제공한다. 리눅스의 시스템콜은 다른 OS보다 상대적으로 갯수가 적고 수행속도가 빠르다. 리눅스는 시스템콜 핸들러 호출 흐름이 간단하기 때문이다. 리눅스는 context switching 속도가 빠르기 때문이
유저모드와 커널모드
kernel
커널은 중요한 자원을 관리하기 때문에, 사용자가 그 자원에 쉽게 접근하지 못하도록 모드를 2가지로 나눈다. 커널모드 운영체제 내부에서 실제로 하드웨어를 제어할 수 있다. 모든 자원(드라이버, 메모리, CPU 등)에 접근, 명령을 할 수 있다. 커널 모드에서 실행되는 모든 코드는 단일 가상 주소 공간을 공유한다. 따라서 커널 모드 드라이버는 다른 드라이버 및 운영 체제 자체와 격리되지 않는다. 유저모드 접근할 수 있는 영역이 제한적이어서 프로그램의 자원에 함부로 침범하지 못하는 모드이다. 여기서 코드를 작성하고, 프로세스를 실행하는 등의 행동을 할 수 있다. 사용자 모드에서 모든 프로세스는 별도의 가상 주소 공간을 할당받는다. Mode bit CPU 내부에 Mode bit 을 두어 kern
이식성
kernel
이식성이란, 특정 시스템 아키텍처의 코드가 (가능하다면) 얼마나 쉽게 다른 아키텍처로 이동할 수 있는지를 의미한다. 이 장에서는 핵심 커널 코드나 디바이스 드라이버를 개발할 때 이식성 있는 코드를 작성하는 방법에 대해서 알아본다. 리눅스는 인터페이스와 핵심 코드는 아키텍처 독립적인 C로 작성됐고, 성능이 중요한 커널 기능은 각 아키텍처에 특화된 어셈블리로 작성해 최적화시켰다. 좋은 예로 스케줄러가 있다. 스케줄러 기능의 대부분은 &x3C;kernel/sched.c> 파일에 아키텍처 독립적으로 구현돼있다. 하지만, 스케줄링의 세부 과정인 context switching과 memory management를 책임지는 switch_to(), switch_mm() 함수는 아키텍처별로 따로따로 구현돼있다.​
커널 모듈
kernel
모듈은 요청 시 커널에 로드 및 언로드할 수 있는 코드 조각이다. 시스템을 재부팅할 필요 없이 커널의 기능을 확장한다. 예를 들어, 한 가지 유형의 모듈은 커널이 시스템에 연결된 하드웨어에 액세스할 수 있도록 하는 디바이스 드라이버이다. 모듈이 없으면 모놀리식 커널을 빌드하고 커널 이미지에 직접 새로운 기능을 추가해야 하고, 새로운 기능을 원할 때마다 커널을 다시 빌드 및 재부팅해야 한다는 단점이 있다. 따라서 모듈을 이용하면 커널 컴파일 시간을 단축할 수 있다. 로드 가능한 커널 모듈(LKM, Loadable Kernel Module)은 런타임에 Linux 커널에 코드를 추가하거나 제거하는 메커니즘이다. 모듈 없이 Linux 커널에 코드를 추가하려는 경우 가장 기본적인 방법은 커널 소스 트
타이머
kernel
커널은 &x3C;asm/param.h> 헤더파일에 시스템 타이머의 진동수를 HZ라는 값에 저장한다. 일반적으로 HZ 값은 100 또는 1000으로 설정돼있고, 커널 2.5 버전부터 ​기본값이 1000으로 상향됐다. 장점: 타이머 인터럽트의 해상도와 정확도가 향상돼 더 정확한 프로세스 선점이 가능해졌다. 단점: 타이머 인터럽트 처리에 더 많은 시간을 소모하고, 전력 소모가 늘어난다. 실험결과 시스템 타이머를 1,000Hz로 변경해도 성능을 크게 해치지 않는다는 결론이 났다. &x3C;linux/jiffies.h>에 jiffies 라는 전역변수에는 시스템 시작 이후 발생한 틱 횟수가 저장된다. 타이머 인터럽트가 초당 HZ회 발생하므로 jiffies는 1초에 HZ만큼 증가한다. 따라서 시스템
파일시스템
kernel
VFS(Virtual FileSystem)는 시스템콜이 파일시스템이나 물리적 매체 종류에 상관없이 공통적으로 동작할 수 있도록 해주는 인터페이스다. 파일시스템 추상화 계층은 모든 파일시스템이 지원하는 기본 인터페이스와 자료구조를 선언한 것이다. VFS는 슈퍼블록(superblock), 아이노드(inode), 덴트리(dentry), 파일(file) 4가지 객체로 구성돼있다. 슈퍼블록: 파일시스템을 기술하는 정보(+ file_system_type, vfsmount 구조체)를 저장한다. 아이노드: 파일이나 디렉토리를 관리하는 데 필요한 모든 정보를 저장한다. 덴트리: 디렉토리 경로명 속 각 항목의 유효성 정보 등을 저장한다. 파일: 메모리 상에 로드 된 열려있는 파일에 대한 정보를 저장한다. 한 파일
프로세스 관리
kernel
1. 프로세스와 구조체 프로세스는 프로그램 코드를 실행하면서 생기는 모든 결과물이다. 일반적인 의미: 실행 중인 프로그램 포괄적인 의미: 사용 중인 파일, 대기 중인 시그널, 커널 내부 데이터, 프로세서 상태, 메모리 주소 공간, 실행 중인 하나 이상의 스레드 정보 등 프로세스는 fork() 호출 시 생성되고, 기능을 수행한 뒤, exit()를 호출해 종료된다. 부모 프로세스는 wait() 호출로 자식 프로세스 종료 상태를 확인할 수 있다. 스레드는 프로세스 내부에서 동작하는 객체이고, 개별적인 PC, Stack, Register(context)를 가지고 있다. 리눅스 커널은 프로세스와 스레드를 구분하지 않는다. 리눅스 커널에 대한 접근은 오직 시스템 콜과 ISR로만 가능하다. 커널
프로세스 스케줄러
kernel
1. 정의 및 역사 스케줄러는 어떤 프로세스를 어떤 순서로 얼마나 오랫동안 실행할 것인지 정책에 따라 결정한다. 스케줄러는 시스템의 최대 사용률을 끌어내 사용자에게 여러 프로세스가 동시에 실행되고 있는 듯한 느낌을 제공해야 한다. 스케줄러는 비선점형 스케줄러와 선점형 스케줄러로 나뉜다. 선점형 스케줄러는 일정한 timeslice 동안 전적으로 프로세서 자원을 사용할 수 있고, 시간이 지나면 다음으로 우선순위가 높은 프로세스에 선점된다. 1991년 리눅스 첫 버전부터 2.4 버전까지는 단순한 스케줄러를 제공했다. 2.5 버전부터 대대적인 스케줄러 개선작업을 통해 O(1) 스케줄러라는 이름의 새로운 스케줄러를 구현했다. Timeslice 동적 계산이 O(1)에 수행되며 프로세서마다 별도의 wait qu
Linux Package
linux
리눅스 패키지(Linux Package)란 리눅스 시스템에서 소프트웨어를 실행하는데 필요한 파일들(실행 파일, 설정 파일, 라이브러리 등)이 담겨 있는 설치 파일 묶음이다. 패키지는 종류는 소스 패키지(Source Package)와 바이너리 패키지(Binary Package)가 있다. 소스 패키지(Source Package)는 말 그대로 소스 코드(C언어..등)가 들어 있는 패키지로 컴파일 과정(configure,make,make install 명령어)을 통해 바이너리 파일로 만들어야 실행할 수 있다. 즉, 소스 패키지는 설치할 때 컴파일 작업도 진행되므로 설치 시간이 길고 컴파일 작업 과정에서 오류가 발생할 수 있다. 바이너리 패키지(Binary Package)는 성공적으로 컴파일된 바이너리
Linux 배포판
linux
• RedHat RPM 기반으로 제작된 리눅스 배포판 현재는 기업용 배포판으로 상업적으로 배포하고 있으며, 무료 버전으로는 페도라가 있다. • Fedora RPM 기반. 레드햇 계열 레드햇의 지원을 받아 개발 및 유지보수가 이루어진다. 페도라의 업데이트 후에 문제점을 파악하여 레드햇 리눅스(RHEL)에 업데이트를 반영하는 방식으로 운영되고 있다. • Debian GNU의 후원을 받는 리눅스 배포판 패키지 설치 및 업그레이드가 단순하다. (패키지 관리 – dpkg, apt) • Ubuntu 데비안 계열 영국 회사인 캐노니컬의 지원을 받음 유니티(Unity)라는 고유한 데스크톱 환경을 사용 • Slackware 초창기에 나온 배포판으로 현재까지 살아있는 가장 오래된 배포판이다. 패트릭 볼커딩에
Linux 특징 및 관련용어
linux
리눅스 토발즈가 커널 개발 / 커널: 소스 공개, 누구나 수정 및 패키징하여 자유롭게 배포 가능 GNU(GNU’s Not UNIX) 리처드 스톨만 유닉스와의 호환 + 더 놓은 기능의 운영체제를 만들고자 했던 프로젝트 자유로운 유닉스를 만들고자 함 / 자유로운 소프트웨어 사용 / 상업화 반대 GCC, BASH, EMACS FSF(Free Software Foundation) 자유 소프트웨어: 상업적 목적으로 사용 가능 / 소스 코드 임의로 개작 가능 / 소스 코드 수정 시 반드시 소스 코드 공개 리처드 스톨만 자유 소프트웨어의 생산, 보급, 발전을 목표로 만든 비영리 조직 자유 소프트웨어 재단 / 무료나 공짜의 뜻X, ‘구속되지 않는다’는 관점에서의 자유 라이선스 GPL(General P
Swap메모리
memory
Swap 메모리란, 실제 메모리 Ram이 가득 찼지만 더 많은 메모리가 필요할때 디스크 공간을 이용하여 부족한 메모리를 대체할 수 있는 공간을 의미한다. 실제로 메모리는 아니지만, 디스크 공간을 마치 가상의 메모리처럼 사용하기 때문에 가상 메모리라고 부른다. 실제 메모리가 아닌 하드디스크를 이용하는 것이기 때문에 속도면에서는 부족할 수 있으나 성능의 제약으로 메모리가 부족한 경우엔 유용하게 사용할 수 있다. Swap 메모리 확인 swapon -s 또는 free -h 명령어를 통해 Swap 메모리를 확인할 수 있다. 아직 Swap 메모리를 설정하지 않은 상태이기 때문에, Swap의 total 메모리가 0으로 뜬다. Swap 메모리 설정 Swap 메모리를 설정하기 위해선, 우선 Swap 메모리를 저장할 파일에
VSS, RSS, PSS, USS
memory
VSS (Virtual set size) VSS는 프로세스의 액세스 가능한 전체 주소 공간이다. 이 크기에는 (malloc과 같은 방법으로) 할당되었지만 기록되지 않은 RAM에 상주하지 않을 수 있는 메모리도 포함된다. 따라서 VSS는 프로세스의 실제 메모리 사용량을 결정하는 데 큰 관련이 없다. RSS (Resident set size) RSS는 프로세스를 위해 실제로 RAM에 보관된 총 메모리이다. RSS는 공유 라이브러리를 사용하는 경우에 중복해서 카운팅하기 때문에 정확하지 않다. 즉, 단일 프로세스의 메모리 사용량을 정확하게 나타내지 않는다. PSS (Proportional set size) PSS는 RSS와 달리 공유 라이브러리를 고려하여 비례한 크기를 나타낸다. 세 프로세스가 모두 30
Virtual Networking Interface
network
리눅스는 컨테이너 기술의 기반이 되는 virtual networking 관련 기능들을 제공한다. virtual networking에 자주 사용되는 대표적인 네트워크 인터페이스를 알아보자. Bridge Linux Bridge는 일반적인 네트워크 스위치와 유사하게 동작한다. Bridge는 주로 라우터, 게이트웨이, VM 등에서 패킷을 목적지로 전달(forwarding)하는 역할을 수행한다. Bridge는 STP, VLAN filter, multicast snooping등의 기능도 추가적으로 지원한다. 아래의 소스코드는 리눅스에서 Bridge를 생성하고, 서로 다른 네트워크 인터페이스와 연결하는 과정을 코드로 작성한 예시이다. 이 과정을 거치면, 브릿지를 통해 VM 1, VM 2과 network naemspac
iptables
network
Iptables 방화벽은 규칙을 관리하기 위해 테이블을 사용한다. 이 테이블은 사용자가 익숙한 형태에 따라 규칙을 구분한다. 예를 들어 만약 하나의 규칙이 network 주소 변환을 다룬다면 그것은 nat 테이블로 놓여질 것이다. 만약 그 규칙이 패킷을 목적지로 허용하는데 사용된다면 그것은 filter 테이블에 추가 될 것이다. 이러한 각각의 iptables 테이블 내에서 규칙들은 분리된 체인안에서 더 조직화(organize)된다. 테이블들이 일반적인 규칙의 목적에 의해 정의되는 동안 빌트인 체인들은 그것들을 트리거 하는 netfilter hook들을 표현한다. 체인들은 기본적으로 언제 규칙이 평가될지를 결정한다. 아래는 빌트인 체인들의 이름인데 이것들은 netfilter 이름을 그대로 사용한다. PRE
network namespaces
network
컨테이너는 namespace를 사용하여 같은 host 안에서 자원을 격리한다. network namespace는 도커와 같은 컨테이너에서 네트워크 격리를 구현하기 위해 쓰인다. 기본적으로 호스트는 외부 네트워크와 연결하기 위한 인터페이스와 Routing Table, ARP Table을 가지고 있는데, 컨테이너를 만들면 그 컨테이너에 대한 network namespace가 생성되어서 호스트의 네트워크 인터페이스와 완전히 분리된다. 대신에, 추가적으로 컨테이너 각각에 가상의 인터페이스와 Routing Table, ARP Table을 설정하면 설정대로 통신을 할 수 있게 된다. 호스트에서는 각 네트워크 인터페이스의 네트워크 요소를 확인할 수 없으며, 각 네임스페이스도 호스트가 외부와 통신하기 위해 쓰는 네트워크
ifconfig
주요명령어
ifconfig는 시스템에 설치된 네트워크 인터페이스 정보를 확인하거나 수정하는 명령어이다. ifconfig [인터페이스][옵션] 형식으로 입력하며, 아무 옵션 없이 ifconfig를 입력하면 현재 설정된 네트워크 인터페이스 상태를 보여준다. lo는 루프백 인터페이스로 자기 자신과 통신하는 데 사용하는 가상 장치이며, 흔히 랜카드라고 불리는 유선 네트워크 인터페이스는 eth0, 무선 네트워크 인터페이스는 wlan0라고 명명한다. IP 주소는 호스트에 하나씩 부여되는 것이 아니라 네트워크 인터페이스에 할당되기 때문에 각 네트워크 인터페이스마다 다른 IP 주소를 할당할 수 있다. 내가 테스트해본 서버에서는 embedded NIC인 eno1와 가상 이더넷 인터페이스인 veth, 그리고 lo 등의 여러 네트워크 인
프로세스 관리
process
시스템이 구동 될 때, 커널은 /etc 에 위치한 init 이라는 스크립트를 실행함으로써 시스템 서비스들을 차례대로 시작시킨다. 이 서비스들은 데몬 프로그램(background)으로 구현되어 있기 때문에 로그인하지 않은 상태에서도 필요 작업들을 수행한다. 프로그램은 프로그램을 실행시킬 수 있는데, 이를 부모와 자식 프로세스라고 표현한다. ps 리눅스는 다중 사용자, 사용 작업 시스템이기 때문에 여러 개의 프로세스를 동시에 수행하기 때문에 항상 어떤 프로세스들이 실행되고 있는지 모니터링할 필요가 있다. ps는 이를 위해 현재 시스템에서 실행 중인 프로세스에 관한 정보를 출력하는 명령어이다. Terminal window /proc 디렉터리 이하에 프로세스와 연관된 가상 파일시스템의 내용을 토대로
환경변수와 프로세스
process
환경변수는 시스템의 속성을 기록하고 있는 변수이다. ​일반적으로 프로세스의 환경변수는 프로세스 자신의 정보를 저장하거나 변경하는 용도로 사용된다. 즉, 프로세스 간 통신이 주 목적인 개체는 아니며, 이를 통한 IPC는 부가적인 기능이 된다. 환경변수는 아래 그림처럼 구성된다. 이 환경변수는 보통 Shell에서 정의하고 저장하는,데 Shell에서 프로그램을 실행시키면 프로그램이 시작하는 순간 셸의 환경변수를 모두 복사해서 프로세스이 들고 있게 된다. 따라서 그 이후에 셸의 환경변수를 바꾼다고 해도 이미 시작한 프로그램의 환경변수는 바뀌지 않는다. 이후 새로 시작하는 프로그램의 환경변수가 바뀔 뿐이다. 해당 정보는 pseudo-filesystem인 /proc 안에서 확인할 수 있다. /proc/&x3C;pid
shell
shell
쉘은 사용자가 운영체제의 서비스를 사용할 수 있도록 사용자의 입력을 기반으로 프로그램을 실행해 주는 역할을 한다. 즉, 커널과 사용자 사이의 인터페이스 역할을 담당한다. 커널은 쉘로부터 전달 받은 명령을 기계가 이해할 수 있는 언어로 변환하여 CPU, I/O, 메모리 등 다양한 리소스에 접근해 주는 역할을 한다. 다시 말해, 쉘은 사용자(프로그램)에게 받은 명령을 전달받아 커널이 이해할 수 있도록 해석하여 전달하고, 커널은 하드웨어와 직접적으로 통신한다. 사용자는 시스템 손상 방지를 위해 접근할 수 있는 영역이 제한되어 있어 하드웨어에 엑세스하기 위해선 시스템 콜이라는 특정 작업을 수행해야 한다. 시스템 콜 (System Call) 시스템 콜은 Mode bit를 기반으로 0이면 커널모드, 1이면 사용자 모
fork와 exec
system call
fork pid_t fork(void); 새로운 자식 프로세스를 생성할 때 사용하는 시스템 호출 함수이다. 자식 프로세스는 부모 프로세스의 PCB를 그대로 상속받는다. 함수의 반환값은 자식 프로세스에게 0, 부모에게는 자식 프로세스의 id이다. pid_t vfork(void); vfork()도 fork()와 마찬가지로 자식 프로세스를 생성하는 함수이다. fork()와 달리 자식 프로세스가 먼저 실행됨을 보장한다. 따라서 생성된 프로세스가 exec계열 함수를 이용하여 새 프로그램으로 실행하는 경우에 주로 사용한다. vfork()로 프로세스를 생성한 경우 부모의 주소 영역을 참조하지 않을 것이라고 생각하여 부모 프로세스의 공간을 자식에게 복사하지 않는다. 복사하는 시간이 소요되지 않으므로 fork 보다
thread 관련 systemcall
system call
우선 스레드란, 프로세스 내에 실행되는 흐름의 단위이다. 프로세스는 반드시 1개 이상의 쓰레드를 가지고 있다. 프로세스와 다르게 한 프로세스 안의 스레드들은 메모리 자원을 공유한다. pthread_create pthread_create는 말 그대로 thread를 생성하는 시스템 콜이다. 이 시스템 콜을 사용하는 경우 -pthread 옵션과 함께 컴파일해야 한다. 각 옵션의 의미는 다음과 같다. thread: 성공적으로 함수가 호출되면 이 포인터에 thread ID가 저장된다. 이 인자로 넘어온 값을 통해서 pthread_join과 같은 함수를 사용할 수 있다. attr: 스레드의 특성을 정의한다. 만약 스레드의 속성을 지정하려고 한다면 pthread_attr_init등의 함수로 초기화해야한다.
리눅스 시스템 프로그래밍 프로젝트
system call
선택과목으로 리눅스 시스템 프로그래밍을 수강하며 진행한 프로젝트 코드 및 배운점에 대해 정리한다. 이 프로젝트에서 개발하는 Application은 아래의 기능을 포함한다. Text File(swblocks.txt)에 기록된 S/W 블록 정보로부터 여러 S/W 블록들을 초기화시킨다. 기록된 파일에는 파일 이름과 파라미터가 아래와 같이 세미콜론으로 구분되어 있다. SwBlock1; Param1; Param2; Param3SwBlock2; Param1; Param2SwBlock3; Param1 S/W 블록의 이상동작(블럭 다운) 발생 시 재초기화를 수행한다. 즉, 해당 블록에 해당하는 프로세스를 재시작한다. 각 S/W 블록의 최종 초기화 시간 및 재초기화 횟수를 출력한다. 프로젝트를 동작시켰
페이지 교체 알고리즘
memory
MIN(OPT) 최근 미래에 안 쓰이는거 교체 이론상 베스트인데 실제 상황에선 참조 예측이 안되니 구현 불가능 비교 연구 목적 Random 알고리즘 진짜 랜덤 FIFO 알고리즘 가장 오래전에 들어온 페이지가 희생자 자주 사용되는 페이지 교체가능성 큼 (지역성 고려 없음) LFU(Least Frequently Used) 사용횟수가 가장 적은 페이지가 희생자 구현 비용이 비싸고 성능 별로 초기에만 많이 쓰는건 교체 잘 안됨 방금 들어온 페이지가 잘 교체됨 LRU(Least Recently Used) 알고리즘 가장 오래전에 참조한 페이지가 희생자 지역성에 기반한 알고리즘 Stack, Counter 등을 추가 저장해야해서 HW 지원 필요 NUR(Not Used Recently
교착상태와 스케줄링
process
탐지 detection 교착상태를 탐지하는 알고리즘 필요 즉시할당하지 못하거나 CPU 사용률이 40% 이하로 떨어지는 경우 호출 탐지 자주실행하면 성능 저하 교착상태에 빠진 프로세스를 빨리 발견 -유휴상태 방지 가능 자원할당 그래프를 활용하여 탐지 교착 탐지시 회복(복구)과정 필요 회복 recovery 강제종료 교착을 일으킨 모든 프로세스 중지 (비용큼) 교착이 해결될 때 까지 하나씩 중지 (오버헤드 큼) 교착 프로세스가 점유하는 자원을 다른 프로세스가 선점하게 함 우선순위가 낮은 프로세스 매번 결과를 기록해서 선점 횟수에 따라 할당해주지 않으면 기아 발생 가능성 있음 프로세스 스케줄링 다중프로그래밍 시스템 I/O Burst, CPU Burst 종류 장기스케줄러 (준비-생성) 어떤 프로세
생산자 소비자 문제
process
생산자-소비자 문제(producer-consumer problem)는 여러 개의 프로세스를 어떻게 동기화할 것인가에 관한 고전적인 문제이다. 한정 버퍼 문제(bounded-buffer problem)라고도 한다. 유한한 개수의 물건(데이터)을 임시로 보관하는 보관함(버퍼)에 여러 명의 생산자들과 소비자들이 접근한다. 생산자는 물건이 하나 만들어지면 그 공간에 저장한다. 이때 저장할 공간이 없는 문제가 발생할 수 있다. 소비자는 물건이 필요할 때 보관함에서 물건을 하나 가져온다. 이 때는 소비할 물건이 없는 문제가 발생할 수 있다. 이 문제를 해결하는 것을 생산자-소비자 협동이라 하며, 버퍼가 동기화되어 정상적으로 동작하는 상태를 뜻한다. 문제를 해결하기 위해 세마포어를 활용할 수 있다. 방법 1 변수 Em
임계영역과 상호배제
process
임계 영역(Critical Section) 공유자원에 접근하는 프로세스 내부의 코드 영역으로 어떤 한 프로세스가 한 영역의 데이터를 사용하고 있을 때, 다른 프로세스가 그 영역의 데이터를 같이 사용한다면 코드상에서 문제가 발생할 수 있다. 따라서 문제가 발생하지 않도록 특정 영역 내의 한번에 하나의 프로세스만 이용하게끔 보장해야해한다. 그러한 영역을 임계영역이라고 부든다. 임계 영역의 문제를 해결하기 위해서는 아래 3가지 조건을 충족해야 한다. 상호배제 하나의 프로세스가 임계 영역에 들어가있다면 다른 프로세스는 들어갈 수 없어야 한다. 진행 임계 영역에 들어간 프로세스가 없는 상태에서 들어가려 하는 프로세스가 여러개라면 어느 것이 들어갈지 결정해주어야 한다. 한정 대기 다른 프
프로세스의 개념
process
프로세스(process)는 컴퓨터에서 연속적으로 실행되고 있는 컴퓨터 프로그램을 의미한다. 프로세스 내부에는 최소 하나의 스레드(thread)를 가지고있는데, 실제로는 스레드(thread)단위로 스케줄링이 이뤄진다. 하드디스크에 있는 프로그램을 실행하면, 실행을 위해서 메모리 할당이 이루어지고, 할당된 메모리 공간으로 바이너리 코드가 올라가게 된다. 이 순간부터 프로세스라 불린다. Processs memory Code 영역 : 프로그램을 실행시키는 실행 파일 내의 명령어(소스코드) Data 영역 : 전역변수, static 변수 Heap 영역 : 동적할당을 위한 메모리 영역. C언어 : malloc &x26; free // C++ : new &x26; delete // JAVA : new 등 Stac
프로세스의 관리
process
대부분의 시스템에서 프로세스는 동시에 실행될 수 있고, 이들은 동적으로 생성되거나 삭제될 수 있다. Process Creation (프로세스 생성) 프로세스는 트리(계층) 구조로 되어있다. 프로세스는 PCB에 저장된 pid(process identifier)값을 통해서 식별되고 관리된다. 또 프로세스는 자원이 필요한데, 자원은 운영체제로 부터 받거나 부모와 공유한다. 프로세스 생성 세부 작업 순서 새로운 프로세스에 PID 할당 주소 공간과 PCB 공간 할당 PCB 초기화(프로세스 상태, 카운터 등 초기화, 자원 요청 등) 링크 걸기 (해당 큐에 삽입) fork() 프로세스의 생성은 fork() 시스템 콜을 이용한다. fork()를 이용하면 부모를 그대로 복사하여 현재 프로세스와 pid만
디스크 시스템
os
프로세서: 논리적 상호작용 드라이버: 구동모터, 엑세스암, 입출력 헤드로 구성 제어기: 드라이버의 인터페이스 명령받아 작동 드라이버 번호, 표면 번호, 트랙 번호 사용 디스크 구조 트랙: 동심원 실린더: 헤드 안움직이고 접근 가능한 범위, 동일 위치 트랙 집합 섹터: 부채꼴 모양으로 나눈 조각, 블록의 집합 디스크 주소 물리주소: 제조사마다 다름 Cylinder, Surface Sector 논리주소: Block 번호 Disk Driver가 변환해줌 디스크 접근 시간 탐색시간: 현재 to 목적트랙 회전지연시간: 트랙 to 목적섹터 전송시간: 데이터 읽고 전송 데이터 전송시간: 탐색시간 + 회전지연시간 + 전송시간 디스크 스케줄링 평가기준 처리량: 시간당 처리수 탐색시간: 헤드 이동
반도체 8대 공정
os
1. 웨이퍼 제조 반도체 집적회로의 핵심 재료인 웨이퍼가 만들어지는 공정이다. 모래를 고온으로 녹인 후 정제하여 정제된 실리콘을 추출한다. 진공의 도가니에 실리콘을 넣고 단결정 실리콘인 시드를 돌려가며 꺼내면 잉곳이라고 불리는 실리콘 기둥이 만들어진다. 다이아몬드 톱을 이용하여 잉곳을 원통 모양으로 다듬은 후, 얇은 슬라이스로 절단하고 연마한다. 아래는 완성된 웨이퍼의 모습이다. 2. 산화 공정 이후 공정을 위해 웨이퍼 위에 산화막을 만들어주는 단계이다. 800~1200도의 고온에서 산소나 수증기를 표면과 반응시켜 만든다. 3. 포토 공정 빛을 이용하여 회로 패턴이 담긴 마스크를 웨이퍼 위에 그리는 공정이다. 감광액을 씌우고 빛을 통과 시켜 회로 패턴을 그린다.
엑세스 제어
보안
적절한 권한을 가진 사람만 특정 시스템이나 정보에 접근할 수 있도록 통제하는 것 컴퓨팅, 통신, 정보자원 등에 대하여 허가되지 않은 접근을 방어할 수 있다. 시스템의 보안 수준을 갖추는 기본 수단 사용자가 자원에 대해 얼마만큼의 권한을 가질지 지정해야 한다. 사용자 엑세스 제어와 데이터 엑세스 제어로 나뉜다. 사용자 접근 제어 사용자가 시스템에 접근하거나 정보를 요청할 때 그 사용자가 누구인지 확인하고 그 사용자가 해당 정보에 접근할 권한이 있는지 확인하는 과정 식별할 수 없는 사용자가 침투하는 것을 방지함 주로 토큰을 사용해 사용자 권한 구별 웹 서버로 치면 JWT로 유저 식별하고 인가하는 동작이 여기에 속함 Window의 예시 사용자가 로그인하면 시스템이 해당 사용자에 대한
운영체제 유형
os
다중 프로그래밍 시스템 (Multi Programming System) 장점 CPU 사용률이 증가하여 많은 사용자의 프로그램이 거의 동시에 할당받는 듯한 느낌을 준다. 즉, 프로세서 사용을 최대화한다. 단점 메모리 관리나 프로세스 정보 보관이 복잡하다 여러 작업이 준비를 갖추고 있을 떄 다음 작업을 선택할 알고리즘이 정의되어있어야 한다. -스케줄링 시분할 시스템 (TSS, Time Sharing System) 다중 프로그래밍을 논리적으로 확장, CPU가 다중 작업을 교대로 수행해서 다수의 사용자가 자원을 공유할 수 있도록 한다. 각 프로그램에 일정한 CPU 사용시간(time slice) 또는 규정 시간량 (quantum) 할당을 주고 컴퓨터와 대화하는 형식으로 실행한다. 응답시간을 최소화할
유저, 커널레벨 스레드
os
유저레벨 스레드(Green Thread) 유저 레벨 스레드는 VM이나 Library 등에서 관리되는 스레드이다. 프로그래밍언어를 사용해서 Thread 라이브러리를 당겨와 스레드를 만들면 유저레벨 스레드가 생성된다. 커널은 사용자 레벨 스레드의 정보를 가지고 있지 않고, 사용자 레벨 스레드가 실행되기 위해서는 커널 스레드의 도움을 받아야 한다. 커널레벨 스레드(Native Thread) 커널 레벨에서 생성되는 스레드로, 실제 스레드 동작을 관리하는 주체이다. 커널이 직접 스케줄링하고, 스레드에 관한 정보를 커널이 직접 가지고 있다. 커널 레벨 스레드를 여러개 만들면 동시에 여러 CPU코어에 CPU burst를 요청할 수 있다. 만약 유저레벨 스레드가 커널 레벨 스레드와 1:1로 연결되어있고, CPU코어가 8개
GTM
tools
GTM은 ‘코드추적을 용이하게 해주는 도구이자 태그 관리 툴’이다. 기존에는 Google Analytics(GA), 페이스북 픽셀 등과 같은 트래킹 툴을 각각 설정해야 했다. 하지만 GTM은 트래킹을 위한 코드의 삽입, 수정, 삭제 모두를 효율적으로 관리할 수 있게 해준다. GTM 코드만 삽입하면, 새로운 마케팅 툴을 여러 개 추가하더라도 추가적인 코드작업 없이 손쉽게 설치 할 수 있다. 핵심 용어 태그 데이터를 어디로 전달할 지를 정의한다. 데이터를 추적해 활용하는 트레이싱 툴을 등록하면 된다. 트리거 어떤 경우에 실행할 지를 정의한다. 트리거 조건을 충족했을 경우 데이터가 전송된다. 트리거 유형은 사용자의 창 로드, 클릭, 스크롤 등이 될 수 있다. 변수 어떤 데이터, 값을 전달할 지를
GitFlow
flow
Git Flow 는 2010년 Vincent Driessen 이 작성한 블로그 글을 통해 유명해지기 시작한 Git Branching Model중 하나로, Git의 사용 방법론이다. GitFlow는 프로젝트를 런칭한 이후에도 코드를 관리하기 용이하게 하고, 프로젝트에서 발생하는 다영한 워크플로우의 구현이 가능하기 떄문에 많은 개발자들이 사용하는 방법론으로 자리잡게 되었다. 에디터와 IDE에서 플러그인으로 지원하는 경우도 많다. 브랜치의 종류가 많아 복잡하고, release와 master의 구분이 모호하기도 하지만 프로젝트의 규모가 커지면 커질수록 소스코드를 관리하기에 용이하다는 장점이 있다. GitFlow의 브랜치 Git Flow는 크게 5개의 branch 를 사용한다. 그중 가장 중심이 되는 브랜치는
GithubFlow
flow
GitFlow의 브랜치 전략의 복잡한 부분을 생략하여 간략화한 브랜치 전략이다. github flow는 master 브랜치 하나만을 가지고 진행하는 방식이다. GitHub Flow는 master와 feature, 두개의 브랜치로 나뉜다. Github Flow의 개발 과정은 다음과 같다. master 브랜치에서 개발이 시작된다. 기능이나 버그에 대해 issue를 작성한다. 팀원들이 issue 해결을 위해 master 브랜치에서 생성한 feature/{구현기능} 브랜치에서 개발을 진행하고 커밋한다. 개발한 코드를 master 브랜치에 병합할 수 있도록 요청을 보낸다. 즉, pull request를 날린다. pull request를 통해 팀원들간에 피드백을 주고받거나 버그를 찾는다. 모든 리뷰가 이뤄지면
GitLab
git
Gitlab은 Git의 원격 저장소와 코드 리뷰, 이슈 트래커 기능등을 제공하는 소프트웨어로, 설치형 Github라는 컨셉으로 시작된 프로젝트이기 때문에 Github와 비슷한 면이 많다. 1. 패키지 종류 GitLab 패키지는 3가지로 구분된다. GitLab CE : Community Edition으로 설치형이고 아무런 제한 없이 무료 GitLab EE : Enterprise Edition으로 설치형이고 매월 유저당 과금 (참고) GitLab.com : 클라우드형이고 개인이 가입해서 사용하면 무료 2. 기능 Git 저장소 및 관리 프로젝트 생성하면 자동으로 git 저장소가 생성됨 그룹 및 팀원 그룹을 만들고 팀원을 지정해서 그룹 단위로 접근 권한을 관리할 수 있음 업무 관리 마일스톤을 설정
자동커밋
git
기존 TIL Repository는 파일을 추가하거나 수정한 뒤 수동으로 커밋하는 방식으로 운영했다. 하지만 혼자 작성하다보니 버전 관리에 대한 이점도 크게 없고, 생성이나 수정에 대한 커밋을 각각 나눠서 하는게 번거로워서 그냥 하루에 한 번씩 local crontab을 돌려 자동으로 커밋하도록 하는 쉘 스크립트를 작성하였다. 크게 복잡한 내용은 없고 그냥 git . add 한 뒤 커밋하는 것이 전부이다. 단, 작성중이어서 커밋하면 안되는 파일은 접두사에 +를 붙여서 표기하고 gitignore에 커밋되지 않도록 설정해줬다. +로 정한 이유는 명령어상 다른 특별한 의미가 없으면서 파일명 앞에 들어갈 일이 없을 것 같은 기호였기 때문이다. +autocommit.sh를 정의한다. !/bin/bash Y=$(dat
Intellij Profiling tools
tools
IntelliJ IDEA Ultimate를 사용하고 있다면 Profiling tools을 사용하여 애플리케이션에 대한 부가적인 분석 정보를 얻을 수 있다. 세부 기능으로는 애플리케이션의 실행 방식과 메모리, CPU 리소스가 할당되는 방식에 대한 분석을 제공하는 Async Profiler, 애플리케이션이 실행되는 동안 JVM에서 발생한 이벤트에 대한 정보를 수집하는 모니터링 도구인 Java Flight Recorder 등이 있다. 또한 애플리케이션의 특정 시점의 스냅샷으로 메모리를 분석하거나(Analyze memory snapshots) 애플리케이션이 실행되는 도중에도 CPU와 메모리 현황을 실시간으로 확인할 수 있는 기능(CPU and memory live charts)들이 있다. 기능 Profiling A
Spark
tools
Apache Spark는 빅 데이터 워크로드에 주로 사용되는 오픈 소스 분산 처리 시스템이다. Apache Spark는 빠른 성능을 위해 인 메모리 캐싱과 최적화된 실행을 사용하며, 일반 배치 처리, 스트리밍 분석, 기계 학습, 그래프 데이터베이스 및 임시 쿼리를 지원한다. 장점 빠른 성능: Apache Spark는 방향성 비순환 그래프(DAG) 실행 엔진을 사용함으로써 데이터 변환에 대한 효율적인 쿼리 계획을 생성할 수 있다. 또한, Apache Spark는 입력, 출력 및 중간 데이터를 인 메모리에 RDD(Resilient Distributed Dataset)로 저장하므로, I/O 비용 없이 반복 또는 대화형 워크로드를 빠르게 처리하고 성능을 높일 수 있다. 애플리케이션을 신속하게 개발: Apac
Column, Row기반 DB
데이터베이스
Row(행) 기반방식은 전통적인 데이터베이스에서 사용하는 레코드 단위 기반의 저장방식이다. 반면 Column(열) 기반방식은 대용량 데이터를 처리하는 데이터베이스에서 사용하는 열 단위 기반의 저장 방식이다. 그러면 이 두 가지 방식이 어떤 차이점이 있는지 자세히 살펴보자. ​아래와 같은 데이터가 들어있는 테이블이 있다고 가정했을 때에 전통적인 방식의 Row 기반방식은 각각의 행이 고유한 ID 값을 가지고 있게 된다. 데이터베이스가 특정 쿼리에 의해서 데이터를 조회하면 레코드 별로 부여되어 있는 고유한 ID를 찾고 그 레코드의 하나의 행에 종속되어 있는 모든 열의 데이터를 모두 불러온다. 그러면 정작 실제로는 필요하지 않은 열까지도 모두 읽게 되는 비효율적인 동작이 발생하는 것이다.
DBMS와 RDBMS
db설계
💾 DBMS(Database Management System) 넓은 의미에서의 데이터베이스는 일상적인 정보들을 모아 놓은 것 자체를 의미한다. 일반적으로 DB라고 말할 떄는 특정 기업이나 조직 또는 개인이 필요한 데이터를 일정한 형태로 저장해 놓은 것을 의미한다. 사용자들은 보다 효율적인 데이터 관리뿐만 아니라 예기치 못한 사건으로 인한 데이터의 손상을 피하고, 필요할 때 데이터를 복구하기 위한 강력한 기능의 소프트웨어를 필요로 한다. 이러한 요구사항을 만족시켜주는 시스템을 데이터베이스 관리 시스템(DBMS)이라고 한다. 💾 RDBMS(Relational Database Management System) 관계형 데이터베이스는 정규화 이론에 근거한 합리적인 데이터 모델링을 통해 데이터 이상(Ano
데이터모델링
db설계
모델링이란 복잡한 현실세계를 추상화, 단순화, 명확화하기 위해 일정한 표기법으로 모델을 표현하는 기법이다. 마찬가지로 데이터 모델링은 비즈니스를 IT 시스템으로 구축하기 위해 데이터 관점으로 업무를 분석하는 기법으로써, 약속된 표기법으로 데이터의 구조를 표현하는 과정이다. 즉 IT 시스템의 근간이 되는 데이터베이스를 구축하기 위한 분석 및 설계의 과정이라고 할 수 있다. 데이터 모델이 중요한 이유 이유설명파급효과(Leverage)데이터 설계 과정에서 비효율적인 데이터 설계 및 업무 요건을 충족하지 못하는 데이터 설계를 한다면 개발/테스트/오픈/운영의 전 과정에 걸쳐서 엄청난 비용이 발생할 수 있다.복잡한 정보 요구사항의 간결한 표현(Conciseness)좋은 데이터 모델
무결성 제약조건
db설계
무결성이란? 테이블에 중복된 데이터가 존재하거나, 부모와 자식 데이터 간의 논리적 관계가 깨지면 프로그램에 큰 장애가 발생할 수 있다. 데이터 무결성은 이러한 일이 일어나지 않도록 데이터의 정확성, 일관성, 유효성을 유지되는 것을 의미하며, DBMS에서 꼭 신경써야 할 사항이다. 그렇기 때문에 DBMS는 무결성을 지키기 위해 제약조건이라는 기능을 기본적으로 제공한다. 무결성 제약조건의 종류 1. 개체 무결성(Entity integrity) : 기본키는 null 값이 될 수 없음 각 튜플에 접근하기 위해 정의된 기본키가 null값이 되면 튜플의 유일성을 판단할 수 없기 때문에 기본키는 null이 되면 안된다. 2. 참조 무결성(Referential integrity) : 외래키는 참조할 수 있는 값을 가져야함
분산데이터베이스
db설계
분산 데이터베이스는 여러 곳으로 분산되어 있는 데이터베이스를 하나의 가상 시스템으로 사용할 수 있도록 한 데이터베이스이다. 논리적으로는 동일한 시스템에 속하지만, 컴퓨터 네트워크를 통해 물리적으로 분산하여 저장되어있는 데이터들의 모임을 지칭한다. 투명성 분산 데이터베이스의 투명성(Transparency)은 해당 데이터베이스를 사용하는 사용자가 데이터베이스 시스템이 분산되어있는 것을 인식하지 못하고 자신만의 데이터베이스 시스템을 사용하는 것으로 인식하도록 만드는 것이다. 네트워크로 치면 다중 서버환경을 떠올리면 된다. 분산 데이터베이스의 투명성은 여러가지 의미를 지닐 수 있다. 외울 필요는 없고, 분산 데이터베이스의 투명성이 어떤 측면에서, 어떻게 지켜져야하는지에 대한 대략적인 그림을 그릴 수 있으면 충분하다
스키마
db설계
스키마는 데이터베이스의 구조와 제약 조건에 관한 전반적인 명세를 기술한 메타데이터의 집합이다. 스키마는 데이터베이스를 구성하는 데이터 개체(Entity), 속성(Attribute), 관계(Relationship) 및 데이터 조작 시 데이터 값들이 갖는 제약 조건 등에 관해 전반적으로 정의한다. 사용자의 관점에 따라 외부 스키마, 개념 스키마, 내부 스키마로 나눠진다. 외부 스키마(External Schema) 외부스키마는 사용자나 응용프로그래머 각 개인의 입장에서 필요로 하는 데이터베이스의 논리적 구조를 정의한 것이다. 외부스키마는 전체 데이터베이스의 한 논리적인 부분으로 볼 수 있으므로 서브 스키마(Sub Schema)라고도 한다. 하나의 데이터베이스 시스템에는 여러개의 외부 스키마가 존재할 수 있으며
정규화와 반정규화
db설계
💾 정규화(Normalization)란? 정규화는 데이터의 일관성을 지키고 중복을 최소화하기 위하여 데이터를 분해하는 과정이다. 데이터베이스 변경시의 이상현상을 제거하고, 구조를 확장하기 쉽도록 하는 것이 목표이다. 정규형 정규형설명제1정규형속성이 원자성을 가진다. 한 속성이 여러 개의 속성값을 갖거나 같은 유형의 속성이 여러 개 인 경우 해당 속성을 분리한다.제2정규형복합 후보키가 있을때, 후보키에 속하지 않는 속성을 결정하기 위해서 후보키의 전체를 참조해야한다. 부분 함수 종속성을 제거한다.제3정규형일반 속성들 간의 함수 종속 관계가 존재하지 않는다. 이행 함수 종속성을 제거한다.BCNF식별자로 쓰이는 속성이 일반속성에 종속되지 않는다. 후
테이블분할
db설계
한 테이블에 대량의 데이터가 저장된다면, 용량(storage)의 한계와 성능(performence)의 저하가 발생한다. 수평/수직 분할 설계는 테이블 구조를 행또는 열을 기준으로 분할함으로써 로우체이닝, 로우마이그레이션 등의 성능 저하를 예방하는 기법이다. 현상설명로우체이닝(Row Chaining)Row의 길이가 너무 길어서 데이터 블록 하나에 데이터가 모두 저장되지 않고, 2개 이상의 블록에 걸쳐 하나의 로우가 저장되어 있는 형태이다. 하나의 행을 읽을 때 여러개의 데이터 블록을 읽어야 하기 때문에 과정에서 성능이 저하된다.로우 마이그레이션(Row Migration)데이터 블록에서 수정이 발생하면 수정된 데이터를 해당 데이터 블록해서 저장하지 못하는 것을 의미한다. 수평분할(
트랜잭션 ACID와 격리수준
db설계
트랜잭션이란 DB에서 처리되는 논리적인 연산 단위를 의미한다. 1개의 트랜잭션에는 1개 이상의 SQL문이 포함된다. 또한 트랜잭션은 분할할 수 없는 최소의 단위로, 전부 적용하거나 전부 취소하는 ALL OR NOTHING의 개념이다. 트랜잭션은 데이터베이스 서버에 여러 개의 클라이언트가 동시에 액세스 하거나 응용프로그램이 갱신을 처리하는 과정에서 중단될 수 있는 경우 등 데이터 부정합을 방지하고자 할 때 사용한다. 트랜잭션의 목적을 달성하며 각각의 트랜잭션을 안전하게 수행하기 위해선 ACID 조건을 충족해야 한다. ACID 원자성 Atomicity 트랜잭션은 DB에 모두 반영되거나, 전혀 반영되지 않아야 한다. 일관성 Consistency 트랜잭션이 실행을 성공적으로 완료하면 데이터베이스
Data Lake와 Warehouse
데이터베이스
데이터 레이크는 구조화되거나 반구조화되거나 구조화되지 않은 대량의 데이터를 저장, 처리, 보호하기 위한 중앙 집중식 저장소이다. 데이터 레이크는 데이터를 기본 형식으로 저장할 수 있으며, 크기 제한을 무시하고 다양한 데이터를 처리할 수 있다. 저장되기 전에 구조화되지 않기 때문에 데이터 웨어하우스보다 훨씬 빠르게 광범위한 데이터에 액세스 할 수 있다. 장점 Agility: 사전 계획 없이 쿼리, data models 또는 applications을 쉽게 구성할 수 있다. SQL 쿼리 외에도 data lake strategy은 real-time analytics, big data analytics 및 machine learning을 지원하는 데 적합하다 Real-time: 실시간으로 여러 소스에서 원본
RabbitMQ
mq
래빗MQ(RabbitMQ)는 오픈소스인 범용 메시지 브로커 소프트웨어이다. RabbitMQ는 온라인 거래 또는 결제 처리와 같이 처리량이 많은 경우에 성능을 개선하는데 사용될 수 있다. 일반적으로 백그라운드 및 cron 작업을 처리하거나 마이크로서비스 간의 메시지 브로커로 사용된다. RabbitMQ는 가볍기 떄문에 클라우드에 배포하기 쉽다. 여러 메시징 프로토콜을 지원하고 분산형 및 혼합형 구성에서 배포를 지원하여 다양한 상황에 적용이 가능하다. 특징 안정성 및 성능 RabbitMQ를 사용하면 메세지를 신뢰성 있고 빠르게 큐 형태로 전달할 수 있다. 유연한 라우팅 메시지는 큐에 도착하기 전에 교환을 통해 라우팅되므로 복잡한 라우팅이 가능하다. 트레이싱 추적 지원을 제공하여 메시징 시스템이 잘못 작동
메시지큐
mq
동기식 통신 방식은 사용자로부터 요청을 받아서 요청을 다 처리할때까지 서버가 다른 행동을 취하지 못하지만, 메세지큐를 사용해 외부에 요청을 맡긴다면 서버가 보다 많은 사람들의 요청을 빠르게 처리할 수 있다. MQ 사용 구조 클라이언트는 서버에 직접 요청하는 것이 아닌 MQ에 전달한다. 그럼 서버는 MQ로 부터 요청 데이터를 수신해서 처리한다. 만약 서버가 요청을 받을 수 없을 수 없는 상황이라면 해당 요청은 서버가 받을 때까지 MQ에 머무르게 된다. 이런 상황에서 MQ에 다운타임이 발생하면 무용지물이 되어버리기 때문에 많은 MQ가 고가용성을 위해 클러스터링 등을 지원한다. Pub/Sub 모델 Pub/Sub 모델은 Publish/Subscribe의 줄임말로 메세지 기반의 미들웨어 시스템을 말한다.
MySQL Replication
데이터베이스
데이터베이스에서 데이터를 복제하는 방식은 크게 동기 방식과 비동기 방식이 있다. 동기 방식: Master 노드에 데이터 변경이 발생할 경우 Slave 노드까지 (동시에) 적용되는 것을 보장한다. 따라서 Master 노드에 장애가 발생하더라도 (데이터 정합성 문제 없이) Slave 노드를 이용하여 서비스를 이어갈 수 있다. 비동기 방식: Master 노드의 변경과 Slave 노드로의 적용이 시차를 두고 동기화됨 Master 노드에서 변경된 데이터가 아직 Slave에 반영되지 못했을 가능성이 있다. 곧 바로 Slave 노드를 이용하여 서비스를 이어갈 경우 데이터 정합성에 문제가 발생할 수 있다. 이러한 두 가지 방식은 성능과 데이터 정합성(정확성)이라는 두 가지 요소 중 어느 것을 중요하게 취급할
Cassandra
nosql
아파치 카산드라(Apache Cassandra)는 자유 오픈 소스 분산형 NoSQL 데이터베이스 관리 시스템(DBMS)의 하나로, 단일 장애점 없이 고성능을 제공하면서 수많은 서버 간의 대용량의 데이터를 관리하기 위해 설계되었다. 카산드라는 여러 데이터센터에 걸쳐 클러스터를 지원하며 masterless 비동기 레플리케이션을 통해 모든 클라이언트에 대한 낮은 레이턴시 운영을 허용하며, 성능 면에서 높은 가치를 보인다. Amazon의 Dynamo 분산 스토리지 및 복제 기술과 Google의 Bigtable 데이터 및 스토리지 엔진 모델이 결합된 모델로 처음에 단계적 이벤트 기반 아키텍처 (SEDA)를 사용하여 Facebook에서 설계되었다. 특징 여러개의 데이터 베이스가 복제된다. (마스터기준) 짧은 지연 시
Memcached VS Redis
nosql
공통점 in-memory cache이다. key-value 저장을 지원한다. (redis는 다른 구조의 데이터 저장 또한 지원한다.) NoSQL이다. Memcached 장점 1. 정적 데이터 캐싱에 효과적 Memcached는 HTML같은 작은, 정적 데이터를 캐싱할 때 효율적이다. Redis만큼 정교하지는 않지만 내부 메모리관리는 단순한 경우에 매우 뛰어나다. (metadata에 더 적은 작원을 소모하기 때문이다) Strings(유일한 지원 데이터 타입)은 추가처리가 필요없어 읽기 전용에 적합하다. 큰 규모의 직렬화된 데이터는 큰 저장공간이 필요하다. Redis 데이터 구조는 데이터의 모든 형태를 그대로 저장할 수 있다. Memcached는 직렬화된 형태로 데이터 저장하도록 제한적이므로 효과적이다. 따라
NoSQL 데이터유형
nosql
NoSQL이라는 용어는 관계형 데이터베이스(RDBMS) 유형에서 벗어난 경량 DBMS류를 부르게 위한 용어이다. NoSQL에는 다양한 DB들이 있는데, 각 DB에서 데이터를 저장하는 유형은 Key–value store, Document store, Graph 세가지 유형으로 나뉠 수 있다. Key–value store Key–value store(KV) 모델은, 데이터는 키와 값의 쌍으로 컬렉션을 표현하는 모델이다. 연관배열(map, dictionary라고도 함)을 기본 자료구조로 가지고있다. Key–value store는 가장 단순한 non-trivial 데이터 모델이며, 선택적인 키 범위를 효율적으로 검색할 수 있다는 강력한 장점을 가지고 있다. 이 모델은 사전 순서로 키를 유지하는 개별적으로 정렬된 모
NoSQL에는 ACID가 없다고?
nosql
관계형 데이터베이스는 트랜잭션 ACID 원칙을 철저히 지켜서 데이터의 무결성을 지키려 한다. 관계형 데이터베이스는 위의 ACID 원칙을 지키기 위해 위와 같은 절차를 진행하게된다. 각 비율은 수행 작업의 비중을 의미한다. 그래프를 보면 정보유지를 위한 자원을 정말 많이 사용한다는것을 알 수 있다 실질적으로 데이터를 넣고 빼고 하는 부분은 오직 12프로인 Useful Work 만 사용하면되는데 말이다. 따라서 RDBMS가 아닌 NoSQL은, 이러한 전통적인 ACID 원칙을 철저하게 지키지 않는 대신 다른 방법을 통해 속도를 향상시키고 데이터 안전성을 챙긴다. BASE 속성 이러한 NoSQL의 특성과 원칙을 나타내는 BASE원칙이라는 것이 있다. Basically Available, Soft state, Ev
PostgreSQL
postgresql
PostgreSQL(포스트그레스큐엘)은 객체-관계형 데이터베이스 시스템(ORDBMS)이다. 테이블 상속, 함수 오버로딩 등의 기능을 갖추고있으며 복잡한 쿼리와 대규모 데이터베이스를 다룰 수 있도록 한다. PostgreSQL은 현재 세계에서 가장 많이 쓰이는 DBMS 중 하나이다. 다양한 프로그래밍 언어 및 어플리케이션을 지원하여 여러 DBMS 중에서도 특히 개발자들이 선호해 충성도가 높은 편이고, 오픈소스 커뮤니티 또한 상당히 활성화되어 있다. 전 세계에서 개최되는 컨퍼런스나 세미나도 꾸준한 편이다. PostgreSQL은 이러한 장점들을 가지고 있다. 1. 최다 SQL 기능 지원 가장 오랜 기간 개발을 거친 PostgreSQL은 관계형 DB 중에서 최다 SQL을 지원한다. 2. 최다 SQL 표준 지원 SQL
OLAP
데이터베이스
OLAP(Online Analytical Processing)는 데이터 웨어하우스, 데이터 마트 또는 기타 중앙화된 통합 데이터 저장소의 대용량 데이터를 고속으로 다차원 분석하는 소프트웨어이다. 대부분의 비즈니스 데이터에는 여러 차원, 즉 프레젠테이션, 추적 또는 분석을 위해 데이터를 분류하는 기준인 여러 범주가 있다. 예를 들어 매출 수치에는 위치(지역, 국가, 주/도, 매장), 시간(연, 월, 주, 일), 제품(의료, 남성/여성/아동, 브랜드, 유형)과 관련된 여러 차원이 있을 수 있는데, 일반적인 데이터베이스로는 2차원 데이터 밖에 저장할 수 없어 저장 성능이나 구현이 복잡할 수 있다. OLAP는 여러 관계형 데이터 세트에서 데이터를 추출한 후 매우 빠른 처리와 분석을 위해 다차원 형식으로 재구성하여
ON절
sql 쿼리
On절은 조인문을 사용할때 조인할 조건을 설정하기 위한 명령어이다. 조회 결과를 필터링한다는 점에서 Where절과 비슷하지만, 실행 시기와 용도에 차이가 있다. On절은 Where절과 다르게 테이블 조인 이전에 실행된다. 그렇기 때문에 Join할 테이블의 일부 컬럼을 가져오고 싶을 때 ON절을 사용한다. 그러나 Inner join을 사용하는 경우엔 조건의 위치와 테이블의 순서에 무관하게 사용할 수 있다. 왜냐하면 조인하는 두 테이블의 위치관계나, 쿼리 순서에 상관없이 결과가 똑같이 교집합으로 나오기 때문이다. On절은, Outer join을 사용할 떄 의미를 가진다. 두개의 테이블이 있다고 가정해보자. A B -1 32 43 54 6 아래의 쿼리로 Left Outer Jo
ORDER BY절
sql 쿼리
ORDER BY절은 SELECT문에서 조회한 데이터 집합을 특정 칼럼 기준으로 정렬한 후 데이터를 출력하는 역할을 한다. 오름차순(ASC) 또는 내림차순(DESC)로 정렬방식을 지정할 수 있다. 정렬방식을 지정하지 않으면 기본적으로 오름차순이 적용된다. 정렬은 일반적으로 숫자에서는 작은 숫자가 먼저, 날짜형 데이터에서는 이른 시간이 먼저, 문자형 데이터에서는 사전순으로 앞서는 문자열이 먼저로 간주된다. Oracle DBMS에서는 NULL값을 가장 큰 값으로 간주하여 오름차순으로 정렬했을 경우에는 가장 마지막에, 내림차순으로 정렬헀을 경우에는 가장 먼저 위치한다는 특징이 있다. ORDER BY절 쿼리 예제 SELECT *FROM 테이블명1 AORDER BY A.컬럼명1
계층형 질의
sql 쿼리
계층형 질의란 테이블에 계층형 데이터가 존재하는 경우 데이터를 조회하기 위한 구문이다. 계층형 데이터는 동일 테이블에 상위와 하위 데이터가 포함된 데이터를 뜻하고, 엔티티를 순환관계 모델로 설계하는 경우 발생한다. 계층형 질의 사용 방법 쿼리구문설명START WITH계층구조 전개의 시작 위치를 지정하는 구문이다. 루트 데이터를 지정한다.CONNECT BY다음에 전개될 자식 데이터를 지정한다. 자식 데이터는 CONNECT BY 절에 주어진 조건을 만족해야한다.(JOIN)PRIORCONNECT BY 절에 사용되며 현재 읽은 칼럼을 지정한다.PRIOR 자식부모형태를 사용하면 계층구조에서 부모 -자식 방향으로 순방향 전개PRIOR 부모자식 형
서브쿼리
sql 쿼리
서브쿼리란 하나의 SQL문 안에 포함되어 있는 또 다른 SQL문을 말한다. 조인은 조인에 참여하는 모든 테이블이 대등한 관계에 있기 때문에, 조인에 참여하는 모든 테이블의 컬럼을 어디에서든 자유롭게 사용(참조)할 수 있지만, 서브퀴리는 메인쿼리에서 따로 파생되어 생긴 쿼리이기 떄문에 자유로운 참조가 불가능하다. 서브쿼리는 메인쿼리의 컬럼을 모두 사용할 수 있지만, 메인 쿼리는 서브쿼리의 컬럼을 사용할 수 없다. 메인쿼리는 서브쿼리에게 자신의 컬럼을 줄 수 있지만, 서브쿼리의 컬럼을 사용할 순 없다. 반대로 서브쿼리는 메인쿼리가 가지고 있는 컬럼을 사용할 수 있지만, 컬럼을 줄 순 없다. 서브쿼리 사용 위치 서브쿼리 사용이 가능한 위치는 다음과 같다. 똑같은 서브쿼리라도 위치에 따라 다른 명칭으로 불리기도 한
윈도우 함수
sql 쿼리
SELECT문을 통한 작업을 하다보면 결과집합의 각 행과 행의 관계에서 다양한 연산처리를 해야할 떄가 있다. (누적합계, 누적비율, 누적등수 등) 이러한 연산처리를 할 수 있게 하는 것이 바로 윈도우 함수(Window Function)이다. 분석함수라고 불리기도 한다. 윈도우 함수의 종류 순위 함수명설명RANK지정한 기준에 따라 순위를 구하고, 동일한 순위가 있다면 건너뛰고 다음 순위로 산출한다. (1, 2, 2, 4)DENSE_RANK지정한 기준에 따라 순위를 구하고, 동일한 순위가 있다면 건너뛰지 않고 다음 순위로 산출한다. (1, 2, 2, 3)ROW_NUMBER지정한 기준에 따라 순위를 구하고, 동일 순위가 있어도 무조건 순위를 산출한다. (1, 2, 3, ,4)
제약조건
sql 쿼리
제약조건은 테이블에 입력되는 데이터가 사용자가 원하는 조건을 만족하는 데이터만 입력되는 것을 보장한다. 제양조건은 데이터의 무결정을 유지하기 위한 DBMS의 보편적인 방법이다. 제약조건설명PRIMARY KEY테이블에 저장된 행들 중에서 특정 행을 고유하게 식별하기 위해서 사용한다.한 테이블에는 하나의 기본키만 정의할 수 있다.기본키 생성 시 DBMS는 유일 인덱스(Unique index)를 자동으로 생성한다.기본키 칼럼에는 NULL 입력이 불가능하다.기본키는 UNIQUE제약조건과 NOT NULL 제약조건을 만족해야한다.UNIQUE KEY테이블에 저장된 행들 중에서 특정 행을 고유하게 식별하기 위해 생성한다.기본키와 다르게 NULL 입력이 가능하다.N
집계함수
sql 쿼리
집계함수를 이용하면 그룹별 집계 결과를 계산하여 한 행으로 나타낼 수 있다. 대표적인 집계함수는 아래와 같은 것들이 있다. 항목결과COUNT(*)NULL 값을 포함한 행의 수를 출력한다.COUNT(표현식)표현식의 값이 NULL이 아닌 행의 수를 출력한다.SUM(표현식)표현식이 NULL 값인 것을 제외한 합계를 출력한다.AVG(표현식)표현식이 NULL 값인 것을 제외한 평균을 출력한다.MAX(표현식)표현식이 NULL 값인 것을 제외한 최대값을 출력한다.MIN(표현식)표현식이 NULL 값인 것을 제외한 최솟값을 출력한다.STDDEV(표현식)표현식이 NULL 값인 것을 제외한 출력한다.VARIAN(표현식)표현식이 NULL 값인 것을 제외한
집합연산자
sql 쿼리
일반적으로 수학에서 사용되는 집합연산으로는 합집합, 교칩한, 차집합, 곱집합등이 있다. SQL문에서도 각각의 일반집합연산에 해당하는 명령어가 존재한다. 일반집합연산자SQL문설명합집합(UNION 연산)UNION, UNION ALLUNION 연산은 수학적으로 합집합을 하는 연산이다.UNION은 교집합의 중복을 제거한 결과를 나타내기 때문에, 정렬 작업으로 인한 시스템 부하가 일어날 수 있다.UNION ALL을 쓰면 중복 결과를 그대로 보여준다.만일 UNION과 UNION ALL의 출력 결과가 같다면 응답속도 향상, 자원 효율화 측면에서 UNION ALL을 쓰는것이 더 낫다.교집합(INTERSECTION 연산)INTERSECTINTERSECTION은 수학의 교
DB 커넥션 풀
최적화
일반적인 데이터 연동과정은 웹 어플리케이션이 필요할 때마다 데이터베이스에 연결하여 작업하는 방식이다. 하지만 이런 식으로 필요할 때마다 연동해서 작업할 경우 데이터베이스 연결에 시간이 많이 걸리는 문제가 발생한다. 예를들어 거래소의 경우, 동시에 몇천명이 동시에 거래 및 조회 기능을 사용하는데 매번 데이터베이스와 커넥션을 맺고 푸는 작업을 한다면 굉장히 비효율적일 것이다. 이 문제를 해결하기 위해 현재는 웹 어플리케이션이 실행됨과 동시에 연동할 데이터베이스와의 연결을 미리 설정해 두고, 필요할 때마다 미리 연결해 놓은 상태를 이용해 빠르게 데이터베이스와 연동하여 작업하는 방식을 사용한다. 이렇게 미리 데이터베이스와 연결시킨 상태를 유지하는 기술을 커넥션 풀(Connection Pool, CP)이라고 한다.
옵티마이저
최적화
옵티마이저는 사용자가 요청한 SQL문에 대한 최적의 실행 방법을 결정하는 역할을 수행한다. 이떄, 옵티마이저가 도출한 실행 방법을 실행계획이라고 한다. 사용자의 요구사항을 만족하는 결과를 추출할 수 있는 다양한 실행 방법들을 도출한 후, 그중에서 최적의 실행 방법을 결정하는 것이 옵티마이저의 역할이다. 비절차형 언어를 사용하는 경우 필요한 요소중 하나이다. 옵티마이저가 실행 계획을 모색하는 방법에는 룰 기반과 비용 기반이 있다. 룰 기반은 정해진 규칙에 따라 SQL문을 도출하는 방식이고, 비용기반은 다양한 DBMS의 객체정보 및 통계정보를 활용하여 최적의 실행 계획을 도출하는 방법이다. 룰 기반에 비해선 비용기반이 상황에 맞게 효율적인 쿼리를 생성할 수 있기 때문에, 오라클 10 이후 버전부터는 공식적으로
조인 수행원리
최적화
조인이란 2개 이상의 테이블을 하나의 집합으로 만드는 연산이다. FROM 절에 2개 이상의 테이블 혹은 집합이 존재할 경우 조인이 수행된다. 조인은 3개 이상의 테이블을 조인한다고 하더라도 특정 시점에는 2개의 테이블 단위로 조인된다. A, B, C 테이블을 조인한다고 하면 A, B를 조인한 후 해당 결과로 나온 집합을 C와 조인하는 방식이다. 각각의 조인 단계에서는 서로 다른 조인 기법이 사용될 수 있다. 조인 기법 조인 기법의 종류에는 NL 조인, 소트 머지 조인, 해시 조인이 있다. NL 조인 (Nested Loops Join) NL 조인은 첫 번째 집합의 대상 건수만큼 반복하면서 두 번째 집합을 조회하여 매칭되는 행을 리턴하는 조인 기법이다. 한 레코드(행)씩 순차적으로 진행하기 때문에 처리 범위가
Procedural/Nonprocedural DML
쿼리종류
DML은 사용자가 DB에서 원하는 데이터를 처리할 수 있도록 명세하기 위한 도구이다. 간단하게 말하면 테이블의 데이터를 입력/수정/삭제/조회하는 데 쓰이는 쿼리 명령어라고 할 수 있다. DML은 데이터 처리를 명세하는 방법에 따라 두가지 유형으로 나눌 수 있다. 절차적 데이터 조작어(Procedural DML) 절차적 데이터 조작어는 사용자가 무슨 데이터(What)를 원하며, 그것을 어떻게(How) 접근하여 처리할지 명세해야하는 초급 데이터 언어이다. 이런 데이터 조작어는 데이터 베이스로부터 한 번에 하나의 레코드(One-record-at-a-time)를 검색해서 호스트 언어(해당 응용 프로그램을 작성하는데 사용된 범용 프로그래밍 언어)와 함께 처리하는 특성을 가지고 있다. 비절차적 데이터 조작어(Nonpr
TCL
쿼리종류
TCL은 트랜잭션 제어어를 뜻한다. 트랜잭션이란 DB에서 처리되는 논리적인 연산 단위를 뜻하는데, TCL은 데이터의 변경 후 커밋, 롤백으로 트랜잭션을 완료, 취소하는 작업을 수행할 때 사용한다. 주의점 단, 아래의 경우에는 TCL 명령어와 상관없이 트랜잭션 적용 처리가 일어난다. DDL문이 실행되었을 경우(이전에 실행됐던 DML문도 함께 커밋된다) DB에 대한 접속을 정상적으로 종료한 경우 위와 같은 상황에서는 트랜잭션이 비정상적으로 처리될 위험이 있으므로 데이터베이스 사용 시 꼭 주의해야한다. TCL 쿼리 예제 커밋 COMMIT; 롤백 ROLLBACK; 세이브포인트 SAVEPOINT SVPT; 세이브포인트까지 롤백 ROLLBACK TO SVPT;
Mock과 Spy
testcode
Mockito 등의 라이브러리를 쓰다보면, Mock과 Spy를 사용하게 될 것이다. 둘 다 클래스의 가상 객체를 만들어서 메소드와 필드를 모의 실험하기 위해 쓰인다는 공통점이 있다. 그렇다면 차이점은 무엇일까? 비교 간단히 말하자면, Mock은 완벽한 가짜 객체를 만드는데 반해, Spy는 기본적으로 기존에 구현되어있는 동작을 따르고 일부 메소드만 stub 한다. Mock 객체의 함수를 호출했을때 그 함수에 stub된 동작이 없으면 코드나 라이브러리에 따라 문제가 생길 수 있다. strict 하게 규칙이 설정된 라이브러리(ex. mockk)의 경우에는 호출 즉시 예외가 던져질 수 있고, null이나 기본값 (int = 0, String = ""...)이 반환되도록 되어있을 수도 있다.(ex. mockito)
Channel
coroutine
Channel은 2개의 Coroutine 사이를 연결한 파이프라고 생각하면 된다. 이 파이프는 두 Coroutine 사이에서 정보를 전송할 수 있도록 한다. 하나의 Coroutine은 파이프를 통해서 정보를 보낼 수 있고, 다른 하나의 Coroutine은 정보를 받기위해 기다린다. 이 채널을 통한 두 Coroutine간의 커뮤니케이션은 공유메모리가 아닌, 커뮤니케이션을 통해서 이뤄진다. Thread는 어떻게 Communicate 할까 소프트웨어를 만들면서 Resource를 Blocking하는 작업, 예를 들면 네트워킹이나 DB를 사용하거나 아니면 계산이 필요한 작업을 할때 우리는 그 작업들을 쓰레드로 분리한다. 이 쓰레드간에 공유할 자원이 필요할때 우리는 두개의 쓰레드가 동시에 그걸 쓰거나 읽게 하지 못하도
코루틴
coroutine
프로그래밍 언어에는 루틴이라는 개념이 있다. fun main() { ... val addedValue = plusOne(value)} fun plusOne(value: Int) { return value + 1} 위와 같은 코드가 있다고 했을떄, main 함수가 메인루틴이고 함수를 호출해서 이동하는 것은 서브루틴이라고 부른다. 서브루틴은 진입하고, 빠져나오는 지점이 명확하다. 메인 루틴이 서브루틴을 호출하면, 서브루틴의 맨 처음 부분에 진입하여 return문을 만나거나 서브루틴의 닫는 괄호를 만나면 해당 서브루틴을 빠져나오게 된다. 그리고 진입점과 탈출점 사이에 쓰레드는 블락되어있다. 우리가 보통 짜는 코드는 이렇게 동작한다. 그러나 코루틴(Coroutine)은 조금 다르다. 코루틴 함수는
netty 사례연구
비동기
파일을 업로드하면 그 파일을 순간 공유할 수 있도록 하는 플랫폼이 있다고 해보자. 그 파일 자체는 아마존 S3에 저장된다. 간단한 업로드 흐름을 구축하자면 아래와 같이 할 수 있다. 전체 파일을 수신한다. S3로 업로드한다. 이미지인 경우 섬네일을 생성한다. 클라이언트 애플리케이션에 응답한다. 여기에서는 2단계와 3단계가 병목 지점이 될 수 있다. 클라이언트에서 서버로 아무리 빠른 속도로 업로드하더라도 실제 드롭을 생성하고 클라이언트에 응답하려면 업로드가 완료된 후 파일을 S3로 업로드라고 섬네일을 생성할 때까지 오랫동안 기다려야했다. 파일이 클수록 대기 시간은 길었고, 아주 큰 파일의 경우 서버로부터 응답을 기다리다가 시간이 만료되는 경우도 있다. 업로드 시간을 줄이기 위한 두가지 다른 방법이 고안됐다
Reactor Pattern과 event loop
reactor
Reactor 패턴은 동시에 들어오는 여러 종류의 이벤트를 처리하기 위한 동시성을 다루는 디자인 패턴 중 하나이다. Reactor 패턴은 관리하는 리소스에서 이벤트가 발생할 때까지 대기하다가 이벤트가 발생하면 해당 이벤트를 처리할 수 있는 핸들러(handler)에게 디스패치(dispatch)하는 방식으로 이벤트에 반응하며, ‘이벤트 핸들링(event handling)’, event loop 패턴이라고도 부른다. Reactor 패턴은 크게 Reactor와 핸들러로 구성된다. namedescriptionReactor무한 반복문을 실행해 이벤트가 발생할 때까지 대기하다가 이벤트가 발생하면 처리할 수 있는 핸들러에게 디스패치한다. 이벤트 루프라고도 부흔다.Handler이벤트를 받아 필
authn과 authz
개발
정보 보안에는 인증(Authentication, authn)와 인가(Authorization, authz)라는 개념이 있다. 간단히 말하자면 authn은 정체성 또는 그 유저가 누구인지와 관련있는 반면, authz는 권한 또는 누군가가 할 수 있는 것을 다룬다. 둘은 연관되어있지만 서로 다른 개념이고, 유저를 식별하고 접근을 관리하는(IAM)에서 중요한 요소이다. Authentication(authn)이란? authn은 사용자의 신원을 검증하는 행위로서 보안 프로세스에서 첫 번째 단계이며, 사용자 또는 장치가 누구인지(또는 무엇인지)를 확인하는 것을 의미한다. 신분을 확인함으로써 사용자가 합법적인지 확인하고자 하는 것이며, 잘못된 사람에게 정보가 노출되지 않도록 보장한다. 일반적인 authn 방법에는 아래
FineGrained와 CoarseGrained
개발
Fine-grained는 사전적으로 “결이 고운”, “미세한”이라는 의미를 가지고, Coarse-grained는 “결이 거친”, “조잡한”의 의미를 가진다. Grain은 곡식 혹은 낱알을 뜻하는데, 알갱이가 거칠고 큼직큼직헌지, 곱고 세밀한지에 따라서 Coarse와 Fine으로 나누어 표현한다고 이해할 수 있다. Fine-Grained 하나의 작업을 작은 단위의 프로세스로 나눈 뒤, 다수의 호출을 통해, 작업 결과를 생성해내는 방식 예를 들어, Do라는 동작이 있다면 해당 함수를 First_Do(), Second_Do()로 나누어 작업 결과를 생성해냄 다양한 “Flexible System” 상에서 유용하게 쓰일 수 있음 Coarse-Grained 하나의 작업을 큰 단위의 프로세스로 나눈 뒤, “Sin
GraphQL
api 아키텍처
GraphQL은 정확하게 데이터를 요청하는 방법을 설명하는 구문이다. 서로를 참조하는 복잡한 엔티티를 사용하는 애플리케이션의 데이터 모델을 사용하고, 그것을 다양한 방식으로 조회해야 할때 유용하게 사용된다. 최근 GraphQL 생태계는 Apollo, GraphiQL, GraphQL Explorer와 같은 강력한 도구와 라이브러리로 확장되고 있다. GraphQL 동작방식 GraphQL은 GraphQL API에서 만들 수 있는 모든 쿼리와 반환하는 모든 타입에 대해 설명하는 스키마를 정의하는 것으로 시작한다. 스키마 정의 언어(SDL)에서는 엄격한 타입 정의를 사용하기 때문에 스키마 정의가 쉽지 않다. 쿼리 전에 스키마를 통해 쿼리에 대한 유효성 검사를 한 뒤 본 요청이 백엔드 애플리케이션에 도달하면, 전체 스
REST
api 아키텍처
REST는 설계적 제약 조건으로 API 스스로에 대한 설명이 가능하여 수 많은 API 소비자에게 채택될 수 있도록 정의된 API 아키텍처 스타일이다. 오늘날 가장 대중적인 REST API 아키텍처 스타일은 2000년 Roy Fielding의 박사 학위 논문에 처음 소개되었다. REST API는 서버 측에서 JSON 및 XML과 같은 간단한 형식의 데이터로 표현 가능하게 한다. REST 동작 방식 REST는 SOAP만큼 엄격하게 정의되어 있지 않다. RESTful한 아키텍처는 6개의 설계 제약 조건을 준수해야 한다. 일관성 있는 인터페이스 : 장비 또는 애플리케이션 타입과 무관하게 목표 서버와 통신하도록 일관성 있는 통신 방법을 허용한다. 무상태 : 요청 자체가 요청을 처리하는 데 필요한 상태이고 서버와 세
RPC
api 아키텍처
RPC란 원격 프로시저 호출이라는 뜻으로, 다른 컨텍스트에서 함수의 원격 실행을 허용하는 사양이다. RPC는 로컬 프로시저 호출 개념을 확장한 것이지만, HTTP API 컨텍스트에 포함되는 개념이다. 초기 XML-RPC는 XML 페이로드 데이터의 타입을 보장하기 어렵다는 문제를 가지고 있었다. 그래서 차후의 RPC API는 보다 정형화된 JSON-RPC를 사용하여 SOAP보다 단순한 구조를 지닌 SOAP의 대안으로 인식되었다. 그중 gRPC는 2015년 Google에서 개발한 최신 버전의 RPC이며, 로드밸런싱, 추적, 상태 확인, 그리고 인증을 위한 플러그인을 지원하기 때문에 마이크로 서비스 연결에 매우 적합하다. RPC 동작방식 클라이언트는 원격 프로시저를 호출하고 매개 변수와 추가 정보를 직렬화하여 생
SOAP
api 아키텍처
SOAP는 XML 형식의 고도로 표준화된 웹 통신 프로토콜이다. XML-RPC 출시 1년 후에 SOAP가 출시되었기 때문에 SOAP는 XML-RPC로부터 상당 부분을 물려받았다. 이후 REST가 출시되었을 때, SOAP와 REST는 같이 사용되었지만, 곧 REST만 사용하는 추세가 시작되었다. SOAP의 동작 방식 SOAP 메시지는 다음과 같이 구성된다. 메시지의 시작과 끝을 표시하는 envelop tag 요청 또는 응답 body 메시지가 특정 사항이나 추가 요구 사항을 결정해야되는지에 대한 정보를 나타내는 헤더 요청을 처리하는 도중 발생할 수 있는 오류에 대한 안내 SOAP API 로직은 웹 서비스 기술 언어(WSDL)로 작성된다. 이 API 기술 언어는 endpoint를 정의하고 실행 가능한 모든
DDD
ddd
DDD는 Domain Driven Design, 즉 도메인 주도 설계이다. 도메인을 중심으로 애플리케이션을 설계, 구성하는 방법이다. 도메인(Domain) 도메인이란 ‘소프트웨어로 해결하고자 하는 문제 영역’을 의미한다. 한 도메인은 다시 하위 도메인으로 나눌 수 있고, 도메인들은 서로 연동하여 완전한 기능을 제공한다. 이 도메인은 소프트웨어의 요구사항을 이해하는데 중요한 요소이다. 서비스를 통해 어떤 문제를 해결할 것인지, 어떤 도메인을 다룰 것인지, 도메인끼리의 관계가 어떠한지 확실하게 알아야 요구사항을 제대로 이해하고 개발을 효율적으로 진행할 수 있다. 도메인은 사용자가 누구인가, 어떻게 사용하냐에 따라 같은요소라고 할지라도 계속 바뀔 수 있고, 형태가 고정되어있지 않은 추상적인 요소이다. 하지만 소프
DDD의 아키텍처
ddd
도메인 주도 설계에서는 도메인을 중심으로하여 애플리케이션을 설계, 구성한다. 애플리케이션은 도메인 외에도 표현, 응용, 인프라스트럭처 등의 영억으로 나뉘어있고 각각의 역할을 수행한다. application전체를 구성하는 아키텍처 요소에 대해 알아보자. 대표적으로 DDD에서는 위와 같은 구조의 Layered Architecture를 가진다. 계층별 설명 1. Presentation Layer (표현 계층) 사용자 요청을 해석하고 응답하는 일을 책임지는 계층이다. 사용자에게 UI를 제공하거나 클라이언트에 응답을 보내는 모든 클래스가 포함된다. Client로부터 request를 받아 response를 보내는 API를 정의한다. 2. Application Layer (응용 계층) 사용자의 요청을 전달받아 시
도메인영역
ddd
도메인 영역의 주요 구성요소는 아래 다섯가지가 있다. 요소설명엔티티(Entity)고유의 식별자를 갖는 객체이다.도메인 모델의 데이터를 포함하며, 해당 데이터와 관련된 기능을 함께 제공한다.밸류(Value)고유의 식별자를 갖지 않는 객체로, 주로 개념적으로 하나인 도메인 객체의 속성을 표현할 때 사용된다. (ex. 주소, 배송상태)엔티티의 속성뿐만 아니라 다른 밸류 타입의 속성으로도 사용될 수 있다.애그리거트(Aggregate)애그리거트는 관련된 엔티티와 밸류 객체를 개념적으로 하나로 묶은 것이다.도메인 관계 복잡도를 낮추기 위해 여러 하위 도메인을 독립된 객체군으로 나눈다.리포지터리(Repository)도메인 모델의 영속성을 처리한다.애그리거트 단위로 도메
이벤트 스토밍
ddd
이벤트 스토밍이란 도메인에 관련된 모든 이해 관계자가 모여서 화이트 보드와 포스트잇을 활용하여 이벤트를 중심으로 업무들 간의 상호 연관성을 찾기 위해 진행하는 워크숍 방법론이다. 도메인 전문가와 개발자를 학습 과정에 참여시키기 위해 설계되었고, 모든 사람들이 시각적으로 도메인에 시각적으로 접근할 수 있게 해준다. 이벤트 스토밍을 하는 이유? 이벤트 스토밍의 가장 큰 목적은 도메인지식을 공유함으로써 전체 비스니스가 어떻게 돌아가는지 한눈에 볼 수 있는 지도(타임라인)를 만드는 것이다. 각 도메인 전문가들의 도메인 지식은 모두 분산되어 있기 때문에 한번에 전체 지도를 그리기 힘든데, 이벤트 스토밍은 그 지식을 모아 정리할 수 있도록 한다. 이벤트 스토밍 하는 법 이벤트 스토밍을 하기 위한 준비물은 “포스트잇과
컨트랙트
ddd
바운디드 컨텍스트의 모델은 서로 독립적이지만 바운디드 컨텍스트 자체는 독립적이지 않다. 컨텍스트는 각자 독립적으로 발전할 수 있지만 컨텍스트끼리는 서로 상호작용해야 하기 때문에, 그 사이에는 항상 접점이 생기는데 이를 컨트랙트(Contract) 라고 부른다. 바운디드 컨텍스트 간의 연동, 즉 컨트랙트에 대한 고민은 솔루션 설계에서 평가되고 다뤄져야 한다. 바운디드 컨텍스트간의 연관관계를 나타낸 컨텍스트 맵의 예시이다. 바운디드 컨텍스트 간의 관계는 두 컨텍스트를 작업하는 팀 간의 협력적 특성이나, 설계에 따라 달라질 수 있다. 컨트랙트가 상호작용하는 패턴은 크게 협력형 패턴 그룹과 사용자-제공자 패턴 그룹으로 나뉜다. 또는, 아예 협력하지 않는 분리형 노선을 채택할 수도 있다. 협력형 패턴 그룹(Coop
MSA의 장단점
msa
마이크로서비스 아키텍처의 장점 크고 복잡한 애플리케이션을 지속적으로 전달/배포할 수 있다. (CI/CD) MSA를 구축하면 크고 복잡한 애플리케이션을 지속적 전달/배포할 수 있다. MSA는 다음과 같은 세가지 방법으로 지속적 전달/배포를 실현한다. 테스트성: 지속적 전달/배포를 하려면 자동화 테스트가 꼭 필요하다. MSA는 상대적으로 크기가 작아서 자동화 테스트를 작성하기 쉽고 더 빨리 실행되며, 애플리케이션 버그도 적은 편이다. 배포성: MSA는 독립적으로 배포할 수 있기 때문에 개발자가 자신이 담당한 서비스 변경분을 배포할때 다른 개발자와 복잡한 협의 과정을 거칠 필요가 없다. 그래서 프로덕션에 변경분을 반영하기가 훨씬 수월하다. 자율성, 느슨한 결합: 작은 팀이 여러개 결합되어있는 기술 조직을 꾸려나
메시지 브로커
msa
브로커리스 메시징 브로커리스 아키텍처의 서비스는 메세지를 서로 직접 교환한다. 장점 송신자가 보낸 메시지가 브로커를 거쳐 수신자로 이동하는 것이 아닐, 송신자에서 수신자로 직접 전달되므로 네트워크 트래픽이 가볍고 지연 시간이 짧다. 메시지 브로커가 성능 병목점이나 SPOF(단일 정야좀)가 될 일이 없다. 메시지 브로커를 설정/관리할 필요가 없으므로 운영 복잡도가 낮다. 단점 서비스가 서로의 위치를 알고 있어야 하므로 서비스 디스커버리 메커니즘을 사용해야한다. 메시지 교환시 송신자/수신자 모두 실행중이어야 하므로 강ㅇ성이 떨어진다. 전달 보장같은 메커니즘을 구현하기가 어렵다. 브로커 기반 메시징 메시지 브로커는 모든 메시지가 지나가는 중간 지점이다. 송신자가 메시지 브로커에 메시지를 쓰면 메시지 브로
사가 패턴
msa
사가는 MSA에서 분산 트랜잭션 없이 데이터 일관성을 유지하는 메커니즘이다. 사가는 일종의 로컬 트랜잭션인데, 각 로컬 트핸잭션은 ACID 트랜잭션 프레임워크/라이브러리를 이용하여 서비스별 데이터를 업데이트한다. 주문 서비스의 createOrder() 작업은 6개의 로컬 트랜잭션을 가진 주문 생성 사가로 구현된다. Txn:1 주문 서비스: 주문을 APPROVAL_PENDING 상태로 생성한다. Txn:2 소비자 서비스: 주문 가능한 소비자인지 확인한다. Txn:3 주방 서비스: 주문 내역을 확인하고 티켓을 CREATE_PENDING 상태로 생성한다. Txn:4 회계 서비스: 소비자 신용카드를 승인한다. Txn:5 주방 서비스: 티켓 상태를 AWATING_ACCEPTANCE 로 변경한다. Txn:6 주문
사가 편성
msa
사가는 단계를 편성하는 로직으로 구성된다. 시스템 커맨드가 사가를 시작할 때 해당 편성 로직은 첫 번째 사가 참여자를 정하여 로컬 트랜잭션 실행을 지시하고, 트랜잭션이 완료되면 모든 단계를 실행 될때까지 계속 그다음 사가 참여자를 호출한다. 로컬 트랜잭션이 도중에 하나라도 실패한다면 사가는 보상 트랜잭션을 역순으로 실행한다. 이와 같은 사가를 편성하는 로직은 두 가지 종류가 있다. 종류설명코레오그래피(choreography)의사 결정과 순서화를 사가 참여자에게 맡긴다. 사가 참여자는 주로 이벤트 교환 방식으로 통신한다.오케스트레이션(orchestration)사가 편성 로직을 사가 오케스트레이터에 중앙화한다. 사가 오케스트레이터는 사가 참여자에게 커맨드 메시지를 보내 수행할 작업
시맨틱 버저닝
msa
마이크로서비스 애플리케이션은 클라이언트를 다른 서비스 팀이 이비 개발한 경우가 대부분이기 때문에 서비스 API를 변경하기가 어렵다. 서비스를 클라리언트를 모두 찾아 강제로 업그레이드시키기도 쉽지 않다. 또 요즘은 유지보수시 서버를 내리지 않기 때문에 규칙적인 단계로 서비스를 업그레이드하여 신구버전을 동시에 실행해야한다. 시맨틱 버저닝 명세는 API 버저닝에 관한 유용한 지침서이다. 여기에ㅔ는 버전 번호를 사용하고 증가시키는 규칙들이 면시되어있다. 시맨틱 버저닝은 원래 소프트웨어 패키지의 버저닝 용도로 쓰였지만, 분산 시스템의 API 버저닝에도 사용할 수 있다. Major : 하위 호환되지 않는 변경분을 API에 적용 Minor : 하위 호환되는 변경분을 API에 적용 Patch : 하위 호환되는 오류 수정
통신
msa
MSA에서는 각 서버가 서로 통신함으로써 여러 도메인이 엮인 요청을 처리할 수 있도록 한다. 이때 서버간 통신을 위해 일반적인 IPC인 REST를 사용할 수 있지만, REST는 동기 프로토콜이기 때문에 호출한 서비스가 응답할 때까지 클라이이언트가 대기해야한다는 단점이 있다. 따라서 서비스가 동기 프로토콜로 통신하면 그만큼 애플리케이션 가용성은 저하될 수밖에 없다. 서비스가 모두 HTTP 통신을 사용한다면, 어느 하나의 서버가 내려갔을때 제대로 동작할 수 없다. 동기 상호 작용 제거 이를 해결하기 위해 비동기 만 있는 서비스를 정의해서 해결할 수도 있지만, 어쩔 수 없이 서비스에 동기 API를 포함시켜야 할 경우가 많다. 이런 경우에는 동작을 조금 우회한 비동기 처리 기법을 사용할 수 있다. 비동기 상호 작용
트랜잭션 격리
msa
사가를 사용하는 경우, 여러 서버와 도메인에 걸친 트랜잭션을 보장해줄 수 있지만 트랜잭션의 완전한 격리를 완벽히 보장할 순 없다. 따라서 dirty read나 nonrepeatable read 등의 문제들이 생길 수 있는데, 이런 문제들을 해결하기 위해선 사가의 격리를 위한 전략을 사용해줘야한다. 이를 위한 전략으로는 아래와 같은 것들이 있다. 시맨틱 락(Semantic Lock) 보상 가능 트랜잭션이 생성/수정하는 레코드에 무조건 플래그를 세팅하는 대책이다. 레코드가 아직 커밋 전이라서 변경될지 모르니, 다른 트랜잭션이 레코드에 접근하지 못하도록 락을 걸어놓는 것이다. 그 플래그는 재시도 가능 트랜잭션(사가 완료) 또는 보상 트랜잭션(사가 롤백)으로 인해 해제될 수 있다. 잠금된 레코드를 어떻게 처
트랜잭션 로그 테일링 패턴
msa
메시지 브로커는 보통 메시지를 적어도 한 번 이상 전달한다. 클라이언트나 네트워크, 혹은 브로커 자신에 이상이 있는 경우 같은 메시지를 여러번 전달할 수도 있다. 하지만 이때 메시지를 여러번 전달함으로 인해 중복 메세지가 발생하여 멱등하지 않은 시스템에 지장을 주거나, 메시지 순서가 꼬여 잘못 처리될 수도 있다. 이를 해결하기 위해 ID를 기록하여 검사하거나 DB 폴링 방식을 사용하기도 한다. 이때 사용할 수 있는 정교하고 성능이 꽤 좋은 방식중 하나로는, 트랜잭션 로그 테일링 패턴이 있다. 말 그대로 메시지 릴레이를 통해 DB 트랜잭션 로그(커밋 로그)를 tailing하는 방법이다. 애플리케이션에서 커밋된 업데이트를 각 DB의 트랜잭션 로그 항목(log entry)으로 남긴다. 그리고 그
SOLID
객체지향
1. 단일 책임 원칙 (Single Responsibility Principle, SRP) 하나의 모듈는 하나의 책임만 가져야 한다. SRP를 적용하면 메소드의 책임 영역이 확실해지기 때문에 한 기능이 수정되었을 때 다른 연쇄작용을 일으키지 않는다. 또, 책임을 적절히 분배함으로써 코드의 가독성이 향상되고 유지보수가 용이해진다. 2. 개방 폐쇄 원칙 (Open-Closed Principle, OCP) 소프트웨어 요소는 확장에는 열려있으나 변경에는 닫혀 있어야 한다. 코드를 수정하거나 기능을 추가할 일이 생겨도 기존 구성 요소는 바뀌지 말아야한다. 추상화와 다형성으로 구현할 수 있다. 3. 리스코프 치환의 원칙 (Liskov Substitutiong Principle, LSP) 서브 타입은 기반 타입이 약속한
응집도와 결합도
객체지향
응집도와 결합도는 코드의 관심사와 연결관계가 어느정도로 구분되어있고, 얽혀있는지를 나타내는 정도이며, 모듈의 독립성을 판단하는 두 가지 지표이다. 응집도는 모듈 내부의 기능적인 집중 정도, 결합도는 모듈과 모듈간의 상호 의존 정도라고 할 수 있다. 높은 응집도와 낮은 결합도를 가진 코드가 객체지향적으로 좋은 코드로 여겨지며, 객체지향 원칙 중 개방 폐쇄 원칙(Open-Closed Principle, OCP)과 연관있는 개념이다. 응집도(Cohesion) 응집도는 모듈에 포함된 내부 요소들이 하나의 책임/ 목적을 위해 연결되어있는 연관된 정도이다. 응집도가 높다는 것은, 하나의 모듈또는 쿨래스가 하나의 책임 또는 관심사에만 집중되어있다는 것을 뜻한다. 응집도가 높으면 그 모듈이 처리할 수 있는 기능 중 하나
빌더 패턴
1 생성패턴
빌더 패턴은 복합 객체의 생성 과정과 표현 방법을 분리하여 동일한 생성 절차에서 서로 다른 표현 결과를 만들 수 있게 하는 패턴이다. 빌더 패턴을 사용하면 객체를 생성할 떄 필요한 값만 넣을 수 있다. 그리고 파라미터룰 사용한 생성자가 아니라 변수명을 명시하여 생성하는 것이기 때문에 변수 순서가 바뀌거나 새로 추가될때 유연하게 대처할 수 있고 매개변수가 많아져도 가독성을 높일 수 있다. 구현하는 것이 복잡하기 때문에 직접 구현하면 코드 구조가 읽기 어려워진다는 단점이 있다. Lombok에서 제공해주는 @Builder 어노테이션을 사용하면 Lombok이 자동으로 빌더를 만들어준다. 예시 코드 @Getter@Setterpublic class Pizza { String name; String to
추상팩토리 패턴
1 생성패턴
서로 관련있는 여러 객체를 만들어주는 인터페이스를 만들어 구체적으로 어떤 클래스의 인스턴스를(concrete product)를 사용하는지 감추는 패턴이다. 구체적인 객체 생성 과정을 추상화한 인터페이스를 제공한다는 점에서 팩토리 메소드 패턴과 비슷하지만 팩토리 메소드 패턴은 구체적인 객체 생성 과정을 하위 또는 구체적인 클래스로 옮기는 것이 목적이고, 추상 팩토리 패턴은 관련있는 여러 객체를 구체적인 클래스에 의존하지 않고 만들 수 있게 해주는 것이 목적이라는 점에서 다르다. 예시 코드 @Getter@Setter@AllArgsConstructorpublic abstract class Pizza { private String name; private Sauce sauce; private
팩토리메소드 패턴
1 생성패턴
팩토리 메소드 패턴은 부모(상위) 클래스 코드에 구체 클래스 이름을 감추고, 자식(하위) 클래스가 어떤 객체를 생성할지를 결정하도록 하는 패턴이다. 구체적인 객체 생성 과정을 추상화한 인터페이스를 제공한다는 점에서 추상 팩토리 패턴과 비슷하지만 추상 팩토리 패턴은 관련있는 여러 객체를 구체적인 클래스에 의존하지 않고 만들 수 있게 해주는 것이 목적이고, 팩토리 메소드 패턴은 구체적인 객체 생성 과정을 하위 또는 구체적인 클래스로 옮기는 것이 목적이라는 점에서 다르다. '확장에 대해 열려있고 수정에 대해 닫혀있어야 한다'는 개방-폐쇄 원칙(OCP)을 만족하는 객체 생성 방법이다. 예시 코드 @Getter@Setter@NoArgsConstructorpublic abstract class Pizza {
컴포짓 패턴
2 구조패턴
컴포짓 패턴이란 객체들의 관계를 트리 구조로 구성하여 부분-전체 계층을 표현하는 패턴으로, 사용자가 단일 객체와 복합 객체 모두 동일하게 다루도록 한다. 복합 객체와 단일 객체의 처리 방법이 다르지 않을 경우, 그 관계를 전체-부분 관계로 정의할 수 있는데, 이 전체-부분 관계를 효율적으로 처리하기 위한 디자인 패턴이 컴포짓 패턴이다. 예시 코드 대표적인 컴포짓 패턴의 예시는 파일 디렉토리 구조이다. 내가 있는 폴더가 다른 폴더의 자식 폴더인지, root 폴더인지에 상관없이 똑같이 다룰 수 있다. 컴포짓 패턴을 사용하면 재귀적인 트리 구조를 구현할 수 있다. public interface Composite { String getName(); String getTree(String tab);
프록시 패턴
2 구조패턴
프록시 패턴은 인터페이스를 사용하고 실행시킬 클래스에 대해 객체가 들어갈 자리에 대리자 객체를 대신 투입하여, 클라이언트는 실제 실행시킬 클래스에 대한 메소드를 호출하여 반환값을 받는지 대리 객체의 메소드를 호출해서 반환값을 받는지 모르도록 하는것을 말한다. 프록시 패턴을 사용하면 실제 메소드가 호출되기 이전에 필요한 기능(전처리등의)을 구현객체 변경없이 추가할 수 있고, 구현클래스에 직접 접근하지않고 Proxy를 통해 한번 우회하여 접근하도록 되어있기 때문에 흐름제어를 할 수 있다는 장점이 있다. 예시 코드 public interface HelloService { String run();} public class HelloServiceImpl implements HelloService{ @
플라이웨이트 패턴
2 구조패턴
플라이 웨이트 패턴은 동일하거나 유사한 객체들 사이에 가능한 많은 데이터를 서로 공유하여 사용하도록 하여 메모리 사용량을 최소화하는 패턴이다. 플라이웨이트 패턴에서는 일부 오브젝트의 상태 정보를 외부 자료 구조에 저장하여 플라이웨이트 오브젝트가 잠깐 동안 사용할 수 있도록 전달한다. 예시 코드 @Getter@Setterpublic class Pizza { private String name; private int price; private Dough dough; private Sauce sauce;} 피자가 있다. 이제부터 피자를 아주 많이 만들어서 배송할건데, 만들 때 마다 새 인스턴스로 생성해서 배송하기엔 메모리가 너무 아깝다. 그래서 자주 변하지 않고, 범위가 작은 속성인 도
인터프리터 패턴
3 행위패턴
인터프리터 패턴은 자주 등장하는 문제를 간단한 언어로 정의하고 재사용하는 패턴이다. 인터프리터 패턴을 사용하면 반복되는 문제 패턴을 언어 또는 문법으로 정의하고 확장할 수 있다. 쉽게 말하면, 일정한 형식을 갖춘 텍스트(String)를 해석해서 규칙에 맞는 로직을 실행할 수 있도록 하는 것이다. 어떤 용도로, 어떤 언어를 구현하는지에 따라 정말 다양한 코드가 나올 수 있지만, 보통 명령을 입력받아 해석하는 Parser와 그것을 바탕으로 로직을 실행하는 Expression으로 나뉜다. 예시 코드 항이 2개인 간단한 덧셈, 뺄셈 식 계산을 인터프리터 패턴으로 구현했다. public interface Expression { Integer interpret(String context);} @NoArgsCo
템플릿메소드 패턴
3 행위패턴
템플릿 메소드 패턴은 동작 상의 알고리즘의 프로그램 뼈대를 정의하는 행위 디자인 패턴이다. 템플릿 메소드 패턴은 여러 작업들이 동일한 구조를 갖지만, 일부 동작은 각각 다르게 구현해야할 때 사용된다. 템플릿 메소드 패턴은 전체 실행과정을 구현한 상위 클래스(추상 클래스)와 실행 과정의 일부 단계를 구현한 하위 클래스(구체클래스)로 나뉘며, 추상 메서드를 재정의함으로써 알고리즘의 구조를 변경하지 않고 알고리즘의 특정 단계들을 다시 정의할 수 있게 해준다 예시 코드 public abstract class Human { abstract void Introducing(); void eating() { System.out.println("밥먹기"); } void sleep
디자인패턴
디자인패턴
디자인 패턴이란 프로그래밍을 할 때에 공통적으로 생기는 문제를 해결하고자 설계한 일정한 코드의 패턴이다. 애플리케이션이나 시스템을 디자인하는 과정에서 자주 발생하는 문제를 해결하는데에 쓰이는 형식화 된 관행이자, 재사용 가능한 해결책이기도 하다. GoF 디자인 패턴 종류 디자인 패턴에 대해 다루는 유명한 책 중 하나인 ‘GoF의 디자인 패턴’에서 다룬 디자인 패턴의 종류는 다음과 같다. 1. 생성 패턴 (Credential Patterns) 객체 생성과 관련된 패턴이다. 객체의 생성과 조합을 캠슐화하여 특정 객체가 생성되거나 변경되어도 프로그램 구조에 크게 영향을 받지 않도록 유연하게 설계하는 것이 목적이다. 싱글톤(Singleton) 패턴 클래스의 인스턴스를 오직 한개만 생성하여 제공하는 패턴
위임 패턴(Delegate Pattern)
디자인패턴
소프트웨어 엔지니어링에서 delegate pattern(위임 패턴)은 객체 합성이 상속과 동일하게 코드 재사용을 할 수 있도록 하는 객체 지향 디자인 패턴이다. 상속(inheritance) vs 합성(composition) 객체지향 시스템에서 기능의 재사용을 위해 구사하는 가장 대표적인 기법은 클래스 상속, 그리고 객체 합성(object composition)이다. 클래스 상속 서브클래싱, 즉 다른 부모 클래스에서 상속받아 한 클래스의 구현을 정의하는 것. 서브클래싱에 의한 재사용을 화이트박스 재사용(white-box reuse)이라고 한다. ‘화이트박스’는 내부를 볼 수 있다는 의미에서 나온 말로, 상속을 받으면 부모 클래스의 내부가 서브클래스에 공개되기 때문에 화이트박스인 셈이다. 상속의 장점 컴파