안녕하세요 오랜만에 돌아왔습니다 하하
한동안 개발을 못하다가 요즘 다시 하고 있는데 좋네요. 맘편히 개발하는게 최고인듯
각설하고 어쩌다 홈서버를 구축했는지 어떻게 활용중인지 공유해보겠습니다
구축 계기
출시해보고 싶었던 서비스 이것저것.. 배포 준비를 하다가 기존 AWS 계정은 프리티어 기간이 끝나기도 했고 총 3가지 이유가 있었다.
1. AWS 프리 티어 정책 변경
2025년 7월부터 신규 AWS 계정에 적용되는 프리 티어 정책이 바뀌었다.
예전에는 1년간 거의 무료로 사용할 수 있었지만.. 이제 6개월간 최대 200달러 크레딧만 사용 가능합니다. 이러면 서버비가 매달 5만원 이상 나올것으로 예상 되는데 이를 아껴보고자 했습니다.
한마디로 비용 절감
2. 남는 컴퓨터
결정적으로 집에 놀고 있는 컴퓨터가 있어서 이걸 활용해보기로!
3. 재미?
(이것도 결정적인 이유중 하나)
구축 과정
OS
기존에 설치되어 있던 윈도우는 밀어버리고 Ubuntu Server 24.04 LTS로 설치
홈서버는 모니터 없이 관리할거라 서버 버전으로 선택
버전은 26.04 LTS도 있긴 했는데 OS로 스트레스 받으면 굉장히 피곤하기 때문에 늘 사용하던 24로 설치했다.
OS 설치는 뚝딱뚝딱 하면 되고
과정이나 가이드는 다른 자료가 너무 많아서 생략하겠습니다.
홈 네트워크
이미 구축 되어 있어서 공유기나 모뎀 만질건 없었다.
근데 통신사에서 주는 공유기는 좀 아쉬워서 공유기 쇼핑을 했다. 개발은 장비빨!
구성
이부분이 유의미 할 것 같은데 네트워크 구성, 인프라 구성까지 공유해보겠습니다.
네트워크 구성 - Tailscale + Cloudflare
우선 포트 포워딩을 하지 않았다.
보통 공유기에서 홈서버의 사설 IP를 고정하고 22, 80, 443번 포트를 외부에 열어두는 방식을 많이 사용한다. 하지만 이렇게 하면 해당 포트가 인터넷에 그대로 노출되어 누구나 접근을 시도할 수 있는 상태가 된다.
공개 IP를 대상으로 동작하는 자동화된 스캐너에 포트가 탐지되면 SSH 무차별 대입 공격이나 알려진 취약점을 이용한 접근 시도가 지속적으로 들어올 수 있다.
이를 방어하려면 SSH Key 인증, 비밀번호 및 root 로그인 차단, 방화벽 설정, 로그인 시도 제한 등.. 신경 써야 할 부분이 꽤 많아진다
그럼 어떻게 했느냐.
우선 관리용 접근은 Tailscale 서비스를 사용했다.
Tailescale 알아보기
굳이 알필요는 없지만 동작 방식이 흥미로워서 공유합니다
https://tailscale.com/blog/how-tailscale-works
Tailscale은 WireGuard 기반으로 기기들을 하나의 사설 네트워크처럼 연결해주는 서비스다.
다른 말로는 peer사이 연결을 해주는 서비스고 P2P할때 그 피어다.
그리고 이렇게 뚫은 터널을 배치하는 방식으로 메시 네트워크를 사용한다고 한다.
좀 혼란스러운데 하나씩 알아보자
WireGuard는 무엇인가
공식문서에는 네트워크 상의 노드간 아주 가벼운 암호화 터널을 생성하는 도구(프로토콜)라고 한다.
여기서 노드는 컴퓨터, 컨테이너, VM 모두 포함
구현체도 제공하는데 이게 wireguard-go이고 tailscale에서 이걸 사용한다고 하네요
전통적인 WireGuard 세팅 - 허브앤 스포크 네트워크
Tailscale이 사용하지 않는
전통적으로 Wireguard 기반으로 뚫은 터널을 관리하는 방식이다

그림을 보면 감이 오겠지만 중앙에 게이트웨이를 세우고 이를 통해서 연결을 하는 방식이다
장점
- 세팅하기 쉽다
- 노드끼리 서로를 알고 있으려면 n * (n-1) 개의 엔드포인트 세팅이 필요한데 그게 필요 없다
단점
- 단일 허브가 현대적인 구조가 아니다
- 경로가 비효율적이다

한마디로 경로 비효율 -> 지연 발생이 문제라는 것이다.
풀어서 써보면 대부분 HA 구성을 하면서 수많은 리전, 지역에 노드를 배치하는데
노드와 허브간 거리가 멀어질때 비효율이 발생하고 지연이 발생한다는 말이다.
-> 멀티허브를 언급하는데 tailscale이 사용하는 솔루션이 아니기 때문에 넘어갈게요
Tailscale의 WireGuard 세팅 - 메시 네트워크

결론적으로
앞에서 나온 문제점들 때문에 tailscale은 메시를 선택했고
n(n-1)개의 엔드포인트 관리를 어떻게 하는지에 대한 내용이 나온다.
엔드포인트 설정은 뭘까
Claude에게 물어봤는데 간단하게 이런식이라고 한다.
특히 상대방을 가리키는 Peer쪽 설정을 해야하는 것이라고 한다.
[Interface]
PrivateKey = <내 개인키> # 나만 아는 것, 절대 안 나감
Address = 100.x.x.x/32 # 이 인터페이스의 IP (Tailscale이 할당)
ListenPort = 41641 # 내가 UDP 받을 포트
[Peer] # 상대 노드 하나당 이 블록 하나
PublicKey = <상대 공개키> # 상대를 식별/암호화하는 키
AllowedIPs = 100.y.y.y/32 # "이 IP로 가는 트래픽은 이 peer로 보내라"
Endpoint = 203.0.113.5:41641 # 상대의 실제 물리 주소:포트
Coordination server

이제 공식 문서에서는 WireGuard 암호화 키를 모든 장치에 어떻게 뿌리는지 소개한다.
(위에서 살펴본 Peer쪽에 공개키)
이를 위해 coordination server라는 노드 스프트웨어를 사용한다고 한다.
비유도 나와있는데 공개키를 넣어두는 공용 드롭박스(shared drop box)라고 소개한다.
자세하게 과정도 알려주는데
- 각 노드는 자체적으로 임의의 공개/개인 키 쌍을 생성하고, 해당 공개 키를 자신의 신원과 연결합니다.
- 노드는 조정 서버에 연결하여 공개 키와 현재 노드의 위치 및 소속 도메인에 대한 정보를 남깁니다.
- 해당 노드는 다른 노드들이 조정 서버에 남겨둔 자신의 도메인에 있는 공개 키 및 주소 목록을 다운로드합니다.
- 노드는 적절한 공개 키 세트를 사용하여 WireGuard 인스턴스를 구성합니다.
글에서 예상했다는듯
"그럼 다시 중앙 집중화 방식인 허브앤 스포크 아니야?" 물음에 반박한다.
이런 설정값들만 중앙 집중화로 구성하고
실제 트래픽은 메시 구조이기 때문에 본인들은 부하 상황에도 병목이 생기지 않는다고 설명한다
즉 하이브리드 구조를 사용중인 것이고 이유에 대해 설명하는 이말이 재미있었다
"회사는 중앙 통제(central control)는 원하지만, 데이터의 중앙 병목(central bottleneck)은 원하지 않는다."
맞죠ㅎㅎ
어떤 식으로 구성 되는건지 알아봤고
뒤에는 방화벽, NAT 보안 관련 내용이 나오는데 넘어가겠습니다,,
글이 길어지고 있는데 여기까지 SSH 접근을 어떻게 구성했는지 + Tailscale 좀더 알아보기였고
이제 서비스 배포다
https://developers.cloudflare.com/cloudflare-one/networks/connectors/cloudflare-tunnel/
Cloudflare Tunnel
How Cloudflare Tunnel works in Zero Trust networking.
developers.cloudflare.com
https://blog.aqudi.me/cloudflare-tunnel-home-server-without-port-forwarding
Cloudflare Tunnel로 포트포워딩 없이 홈서버 운영하기
이 글에서 다루는 내용 포트포워딩이 안 되는 이유 (CGNAT 환경 이해) CGNAT 우회 방법들의 장단점 비교 Cloudflare Tunnel 설정 방법 (MacOS 기준) 외부에서 내 PC로 접근할 수 있도록 허용하는 방법을 생각
blog.aqudi.me
서비스 배포는 cloud flare Tunnel 사용했다.

리버스 프록시로 내 서버를 숨기는 구조다
이렇게 해서 TLS, DDOS 방어, WAF, IP 노출 안됨 등 이점이 많다.
나중에 내 서비스가 속도에 문제가 생기고 cloudflare가 병목이 된다면 손봐야겠지만 그럴 가능성은 아직 낮다

이런식으로 로드 밸런싱이나 HA 구성도 가능하다
작동 방식에 특이한건 없어서 넘어가자
인프라 구성
최종적으로 이런 느낌이다

최대한 단순하게 구성했고
nginx도 cloudflare때문에 필요가 없어졌다
한가지 고민되었던건 DB Redis를 docker로 관리할지 직접 설치할지였는데
관리의 단순함을 우선순위로 잡았다. 나중에 성능 문제나 다른 문제가 생기면 바꿔보는 걸로.
그리고 그림에서 오브젝트 스토리지가 앱이랑 연결되어 있는 것이 이상하다고 생각하다고 생각할 수 있을 것 같다. 맞다
지금은 이미지도 많이 없고 가벼워서 저렇게 했는데
결국 직접 서빙, CDN 연결할 일이 생길 것 같은데 그때는 Min iO를 고려중이다.
High Performance Data Store for AI & Analytics | MinIO
Exascale data infrastructure for AI, agentic computing, and analytics. MinIO AIStor natively supports S3 for objects, Iceberg for tables, and SFTP for files.
www.min.io
S3랑 호환 가능하고 뭐 장점이 많다고 하는데 도입하면 공유해보겠습니다
그리는 미래
기술적인 호기심이 많은 편이라
k3s 도입을 고민했다가 단일 서버에는 오버엔지니어링인 것 같아서 참았다
운영하는 서비스가 단일 서버로 버티기 힘들만큼 성장하길 기대하며..
자취방/본가에 HA, 클러스터 구성까지 하는 미래를 꿈꾸고 있습니다람쥐
무럭무럭 자라라.
외주에 배포까지(서버 임대) 해보는 욕심도 있다ㅎㅎ
'PROJECT' 카테고리의 다른 글
| [포스트맨] OAuth 테스트 (1) | 2025.06.17 |
|---|---|
| [Spring] Swagger 트러블 슈팅 (0) | 2025.06.06 |
| [졸프] 출시, BM, 개선사항 (1) | 2025.06.06 |
| [졸프] 3주만에 플러터로 앱 만들기! (0) | 2025.06.06 |
| [졸프] Spring batch, 크롤링 트러블슈팅 (0) | 2025.06.06 |