[카테고리:] 프로그래밍
-
내부 IP만 주는 개발용 VPS 호스팅 불편기
예~~~전에 필자가 아주 어릴때 일이다. 리눅스 위에서 소켓 프로그래밍을 배우려고 하고 있었다. 그 당시만 해도 가상화 시스템이 변변치 않아서 리눅스 가상 서버 호스팅을 받으려고 했었다. 해당 서버에서는 두가지만 됐으면 문제 없었다. 첫번째는 C로 작성된 몇백줄 짜리 코드가 컴파일되고 실행되는것이며, 두번째는 간단한 내 홈페이지를 돌리는 것이다. 그래서, 굳이 외부 IP를 선택할 필요가 없었다. 그래서 내부 IP를…
-
Variance (Covariance, Contravariance) – 제너릭 타입
TL;DR 어떤 제너릭 Type<T> 을 사용할 때, 타입 파라메터 T에서 최초에 지정한 타입 T만 받을 수 있으면 invariant Type<T> 에서 타입 T와 T의 서브클래스 까지 받을 수 있으면 covariant 이다. (List<T>를 파라메터로 함수에 List<TSubClass>를 대신 집어 넣을 수 있다.) Type<T> 에서 타입 T와 T의 슈퍼클래스 까지 받을 수 있으면 contravariant 이다. (Func<T>를 파라메터로 함수에 Func<TSuperClass>를…
-
리눅스 Secondary VNIC 붙이기 (Oracle Cloud): 드라이버 로딩 오류
TL;DR 디도스와의 전쟁 내가 도와주는 서비스 중에 한 곳이 요즘 디도스로 골머리를 앓고 있다. 이 서비스는 분 단위로 디도스를 받고 있다. 한번 공격이 오면 5분간 지속된다. 그러고는 몇 시간 동안 잠잠하다. 잠잠한 기간이 한시간일 때도, 3시간일 때도, 그 다음날이 될 때도 있다. 서버가 다운됐다는 알림을 받고 조치를 취하려고 보면 이미 물러간 뒤다. 이 문제가 몇일…
-
PPT 추가기능 사용시 오류발생
문제 해결 Micorsoft 365가 Office 스토어의 추가기능을 개별적으로 취득하고 실행하지 못하도록 구성되었습니다. 라는 오류는 학교·기업용 계정으로 파워포인트 또는 Office 제품(엑셀, 워드등)을 사용할 때 발생한다. 학교나 회사의 정책상에서 “추가기능 개별 취득 허용”을 켜지 않으면 발생한다. 이 문제를 해결하려면, 조직의 관리자에게 해당 옵션을 켜달라고 해야한다. 아니면 다른 계정이나 로그아웃 한 채로 사용해야 한다. 근본적인 원인은, 해당 조직에서…
-
Syn Flood 방어기 – Oracle Cloud(OCI) 에서
tl;dr VCN 설정중 보안목록 부분에 각 rule의 stateful, stateless 여부를 선택하는 칸이 있다. 커널을 아무리 튜닝해도 SYN Flood로 인해 VNIC의 conn track이 꽉 차버리면 패킷자체가 넘어오질 않는다. 서버 운영중에 SYN Flood를 당하는것 같으면 이 부분을 꼭 확인해 보자. 해당되는 경우, Observation -> Service Matrix에서 “Ingress Packets Dropped by Full Connection Tracking Table” 그래프가 꽉 차는것을 볼 수…
-
SSL 인증서의 DNS 이름을 통한 서버 알아내기
자신의 서버 IP를 숨기기 위해 Cloudflare같은 CDN을 이용하는 경우가 종종있다.. 이러한 CDN(일종의 Proxy 시스템)을 이용하면 DNS 조회를 했을 때 실제 서버의 주소 대신 해당 CDN의 노드 IP주소가 표시된다. 서버의 실제 IP가 노출됨을 막음으로서 DDos공격이나 기본적인 해킹 시도를 줄이거나 어렵게 만들수 있다. CDN이나 표면 서버를 앞에 두면 실제 핵심(코어) 서버의 주소를 가릴수 있다. 그렇지만 서버 프로그램에 설정을 잘 못하면 모두 헛수고가 될 수도 있다. 주의를 가져야 하는 부분은 SSL 인증서의 DNS 필드이다. SSL 인증서에는 발급대상 정보와 “도메인 주소” 주소가 담겨있다. SSL 인증서만 받아낼 수 있으면 해당 서버가 어디에 소속된 서버인지 쉽게 판단할 수 있다는 말이다. 서버의 SSL 인증서는 어떻게 받아낼수…
-
기본적인 SSH 보안 강화
이 글에서는 SSH 접속에 관련된 보안 설정을 다뤄보려고 한다. 대단한것들은 아닐뿐더러 이미 알고 있는 내용도 많을것이다. 들어가기전에 말을 하나 하자면, 서비스(프로그램)을 돌린다면 반드시 root가 아닌, 별도의 서비스 계정을 만들어서 돌리라는 것이다. 아래와 같이 설정을 해봤자, root 권한을 가진 서비스의 취약점에 의해 공격이 뚫리게 되면 아무런 의미도 없어진다. 서비스(특히 외부에 노출되는)를 돌릴때는 반드시 root 미만의 계정에서…
-
KT PC대수 제한 경험기(?) (추가단말 검사로 인한 웹소켓 장애 체험기)
최근에 웹소켓 서비스쪽 작업중에 이상한 문제가 발생했다. 문제가 없던 웹소켓 서버에 접속이 안되는 문제가 발생한 것이다. 새로고침도 여러번 하고 브라우저도 바꾸어보아도 여전히 접속이 불가능했다. 지인분들을 통해 나에게만 발생하는 문제임을 확인했다. 그제서야 뭔가 문제가 있음을 느끼고 무슨일이 일어나고 있는지 살펴 보았다. WS 요청을 했는데 200이 온다고? 가장 먼저 개발자 도구를 열어보았다. 개발자 도구에서 네트워크 패널을 보면 브라우저가 어떻게 통신을 했는지 간단하게 볼 수 있다. 네트워크 패널을 이용하여 웹소켓 요청을 찍어봤는데, 응답 코드로 101이 아닌 200이 오는것을 확인하였다. WS upgrade를 요청하면 101이 나와야 함이 정상인데 200이 온 것이다. 해당 웹소켓 서버는 내가 제작을 한 것이었는데, 기억에 분명 200을 리턴하는 코드는 작성한 적이 없었다. 혹시 특정 상황에서 내가 200을 리턴하도록 한 것이 있나? 해서 살펴 봤는데 전혀 없었다. 또한 저런 응답헤더를 찍어내는 코드는 전혀 없었다. 웹소켓 백엔드 서버에서 발생하는 문제는 아닌것으로 판단하고, 그 앞단을 살펴 보기로 했다. 이 서버는 [유저 -> CDN -> WS서버] 의 접속 구조를 가지고 있다. WS서버의 문제는 아닌것을 확인했으니 CDN을 파 보아야 할 차례였다. 빠르게 해당 CDN을 경유하여 WS를 접속하는 다른 사이트를 찾아보았다. 결과는 정상이었다. 몇번을 시도해 보았고, 수신지 IP가 동일함 까지 확인해 보았다. 테스트 도중 위의 요청 헤더가 이상함을 한번 더 확인하였다. CDN 에서 요청을 내려줬으면 CDN 특유의 헤더가 찍혀야 하는데, 그런것이 전혀 없다. 일단 Response가 나온다는거면 아무리 CDN이 꼬여도 특정 헤더 하나정도는 찍혀야 마땅하다. 즉, 하나 정도는 묻혀 나와야 할 헤더가 없던 것이다. (예를 들어, Cloudflare라면 server: cloudflare 등의 헤더가 있어야 한다) 사실 처음에는 CDN 내부에서 오류가 발생했거나, GET / 요청이 캐싱되어서 GET…
-
(단일) 실패지점
서버를 운영하다 보면 서버 장에 대응에 대한 고민이 생긴다. 서버란 어찌되었건 “끊김이 없어야 하는 것”이다. 단 몇분이라도 서버에 장애가 발생하면 사용자는 불편을 느낄 뿐더러 신뢰성을 잃을수 조차 있다. 쇼핑몰 서버에서 피크 타임시 발생하는 장애는 하루 매출의 반 이상을 잃게 할 수도 있다. 특정 목적의 서비스 중이라면 SLA에 따라 보상금까지 물어야 할 수도 있다. 이해가 쉽도록 “서버”를 “방송”으로 바꾸어보자. 방송사의 장비에 불량이 생겨서 몇 분 동안 검은 화면만 송출되었다고 생각하면 얼마나 큰 일인지 생각할 수 있을거다. 자체 방송중에 검은화면만 나와도 큰 일인데, 광고 타임에 검은 화면만 나왔다면 (계약에 따라) 손해배상을 해야 할 수도 있다. 증상을 조기에 알아낸다고 해도 수정·패치 작업에는 또 긴 시간이 필요하다. IT운영 인력이 부족할 경우 ‘증상이 있음’을 알아내는것 조차 어려울 수 있다. 그렇기에 가장 중요한것은 애초에 장애가 나지 않도록 하는 것이다. 어느 호스팅사에서 월 1만원짜리 웹 호스팅을 받고있다고 하자. 당장 보이는건 해당 호스팅 업체에 있는 내 사이트밖에 없다. 하지만 그 아래에는 서버의 위치 (가정집, 사내, IDC)와 회선 정보, 그리고 서버 관리능력과 안정성이 깔려있다. 사실 이런 걱정을 모두 호스팅사에 넘기기 위해 (Managed) 웹 호스팅을 쓰는것은 맞지만, 어쨋든 장애가 나면 손해는 내가 보는것이다. 단순한 웹서버라고 해도 안을 까보면 상당히 많은 구성요소가 깔려있다. 당장 글을 쓰면서 생각나는것만 해도 서버의 지리적 위치, 인터넷(회선·대역폭), 내부 장비(스위치등 일체), 전기, 무정전 시스템, 네임 시스템 서버, 물리적인 서버, 그리고 그 안에 설치된 소프트웨어 Nginx·Apache등 웹 서버 프로그램, DBMS…
-
유챗 봇 제작 #2 – 접속정보 처리
이전까지의 글에서는 유챗 서버와의 통신에 필요한 맨 아랫 부분을 다루어 보았다. 여기서 부터는 밑바닥에 대한 부분에서 벗어나서 실질적으로 봇을 이용하기 위한 (일종의) 클래스를 구현해 볼 것이다. 글을 쓰는 도중에 tokio가 1.0으로 버전이 올라갔다. 아직 종속된 라이브러리들이 1.0을 지원하지 않아서 0.3버전을 바탕으로 글을 작성하였다. 1.0 버전으로 올리는 과정에 대해서는 따로 글을 쓸 것 같지는 않으니, 필요가 있으면 직접 Github의 리포를 확인해야 할 것이다. 이전글에서는 아래와 같은 코드를 이용해서 직접적으로 접속 정보를 전송하였다: 하지만 위의 코드로는 접속정보를 바꾸기가 쉽지 않다. 여러개의 방에 접속하기 위해서는 매번 접속정보를 생성 해 줘야 하며, 인증 토큰을 필요로 하는 방에 접속하려면 해줄것이 너무 많아진다. 물론 안될 것은 없겠지만 이것들을 직접 구워먹고자 하면 상당히 번거롭고 귀찮은 방법이다. 그러므로 앞으로 접속정보를 관리하는 구조체를 만들어서 관련된 작업은 모두 거기서 이루어 지게 한다. 우선 접속정보를 담아낼 수 있는 구조체를 만든다. cache_token과 profile_image는 uchat.js를 뜯어보면서 ‘이런게 있는구나~’ 를 알아냈다. 실제로는 어떻게 사용되는지 까지는 모르겠다. 겉으로는 드러나지 않지만 계속해서 내부에선 업데이트가 진행되는듯 한 것으로 보아, 언젠가 기능 구현에 쓰일지도 모르겠다. uchat.js를 뜯어봤더니, 무조건 있어야 하는 값은 방 ID 하나 뿐이었다. 접속 인증을 사용하지 않는 방은 token이 필요 없다. nick이 없으면 알아서 손님1234 같은 닉네임을 만들어 준다. auth 또한 Option으로 뺄려면 뺄 수 있으나 구현에 있어서 한단계 추가 할 것이 생겨서 UChatAuthLevel이라는 enum에 None을 추가해 놓는것으로 타협하였다. 값을 설정하는 방식으로는 builder 패턴을 이용하였다. getter / setter를 만들 필요도 없을것 같아서 저 수준에서 마감을 했다. (어짜피 필요하면 구조체 내에 접근 가능하기도 하다) Builder 패턴을 모르는 사람을 위해 설명하자면, 값을 설정하는 함수를 실행하면 자신을 리턴하여 계속 이어서 값 설정을 가능하도록 하는 패턴이다. 아래와 같이 setter를 사용할 수도 있지만, 빌더 페턴에 비해서는 해야 할 것이 더 많다: 빌더 패턴을 이용하면 위의 코드를 더 간단하게 호출할 수 있다. nick()은 닉네임 설정후 빌더(자신)를 그대로 돌려주고, id()도 마찬가지로 자신을 돌려주고 하기 때문에 가능하다. 값이 설정된 빌더를 계속 주고 받고 한다고 생각하면 된다. 이제 필요한 데이터는 모두 모았다. 이제 이것을 실제 접속 정보로 바꾸는 부분이 필요하다. 우선 유챗에서 채팅방 접속 토큰을 어떻게 생성하는지 보자: 여기서 우리가 봐야할 부분은 uchat_array2data() 이다. 한줄한줄 해석해 보자. $arr[‘time’] = time();– 접속토큰 변조 방지를 위해…