SQL(Structured Query Language)은 1970년대 초 발명된 이후 데이터베이스와의 상호작용을 관리하는 기본 수단으로 쓰이고 있다. 스택 오버플로우에 따르면 SQL은 여전히 상위 5개 프로그래밍 언어 중 하나이고 개발자의 약 50%가 업무에 사용하고 있다. 하지만 이런 보편성에도 불구하고 아직도 SQL은 어렵고 부담스럽다는 말을 많이 한다. 그러나 어떻게 작동하는지만 이해하면 SQL은 전혀 어렵지 않다. 더구나 오늘날 기업은 생성되는 데이터에 점점 더 많은 가치를 부여하고 있으므로 SQL을 알면 소프트웨어 개발자로서 더 뛰어난 역량을 발휘하고 경력을 발전시킬 기회를 잡을 수 있다. 개발자가 SQL에 대해 알아야 할 것과 조심해야 할 문제를 정리했다.
SQL을 두려워하지 말라
SQL은 구조적이므로 사용하기 쉽고, 여러 쿼리의 조합 방법을 엄격하게 규정하므로 읽고 이해하기 쉽다. 타인이 작성한 코드를 볼 때 쿼리 구조를 살펴보는 것으로 그 사람이 원하는 것이 무엇인지를 이해할 수 있어야 한다. 이렇게 되면 특히 복잡한 연산과 JOIN에서 향후 쿼리를 튜닝하고 성능을 개선하기도 더 쉬워진다.
그러나 많은 개발자가 처음 접했을 때의 경험을 이유로 SQL을 멀리한다. 큰 이유 중 하나가 처음 배우는 명령인 SELECT의 사용 방법에 있다. 개발자가 SQL을 작성하기 시작하면서 가장 일반적으로 저지르는 실수는, 다루고자 하는 요소를 SELECT로 선택하는 것이다. 그러나 SELECT *처럼 SELECT를 너무 폭넓게 사용하면 성능에 큰 영향을 미칠 수 있고 나중에 쿼리를 최적화하기 어려워진다.
쿼리에 모든 것을 포함해야 하는가, 아니면 더 구체적으로 좁힐 수 있는가? 이 질문은 상황마다 다를 수 있다. 서버가 효율적으로 기능하기 위해 필요한 메모리 공간에 영향을 미치는 방대한 ResultSet 응답으로 이어질 수 있기 때문이다. 쿼리가 다루는 데이터가 너무 많으면 특히 클라우드 서비스에서 데이터베이스를 실행 중인 경우 필요 이상의 메모리를 할당하게 된다. 클라우드에서 사용량은 곧 비용이므로 SQL을 잘못 작성하면 이것만으로도 훨씬 더 많은 비용을 지출하게 될 수 있다.
데이터 형식 알기
개발자가 SQL을 사용할 때 겪는 또 다른 일반적인 문제는 열의 데이터 형식과 관련된다. 개발자가 기대하는 데이터 형식은 크게 2가지로, 정수와 가변 문자, 즉 varchar다. 정수 필드에는 숫자가 포함되지만 varchar 필드에는 숫자와 문자가 포함될 수 있다. 한 가지 형식, 일반적으로 정수를 예상하면서 데이터에 접근했는데 다른 데이터 형식을 받게 되면 예측 결과의 데이터 형식이 일치하지 않게 된다.
이 문제를 피하려면 정기적으로 사용하는 문 명령과 준비된 문 스크립트에 대한 접근 방식에 주의를 기울여야 한다. 그러면 예상과 다른 결과가 발생하는 상황을 방지하는 데 도움이 된다. 마찬가지로, 데이터베이스 테이블을 JOIN할 때도 접근 방식을 점검해서 서로 다른 데이터 형식을 가진 열을 사용하지 않도록 해야 한다. 데이터를 확인하면 JOIN 실행 시 데이터 값이 있는 필드가 잘리거나 데이터 값이 다른 값으로 변환되는 등의 데이터 손실을 방지할 수 있다.
간과하는 경우가 많은 또 다른 문제는 문자 집합, 즉 charset이다. 깜박 잊기 쉽지만, 애플리케이션과 데이터베이스가 작업에서 동일한 charset을 사용 중인지 항상 확인해야 한다. 서로 다른 charset을 사용하면 인코딩 불일치가 발생하고 이로 인해 애플리케이션 뷰가 망가지고 특정 언어나 기호를 사용할 수 없게 된다. 최악의 경우 데이터 손실 또는 디버그하기 어려운 난해한 오류로 이어진다.
데이터 순서가 중요한 경우 알기
데이터베이스 작업을 처음 시작할 때 많은 개발자가 열의 순서가 더 이상 중요하지 않다고 생각한다. 실제로 많은 데이터베이스 제공업체가 개발자는 스키마를 알 필요가 없고 툴이 알아서 다 해준다고 주장한다. 그러나 겉보기에는 영향이 없는 것 같아도, 인프라에 상당한 정도의 계산 비용이 발생할 수 있다. 종량제 클라우드 서비스를 사용하는 경우 이 비용은 무시할 수 없을 정도다.
여기서 중요한 것은 데이터베이스와 인덱스가 천차만별이라는 사실을 이해하는 것이다. 예를 들어 복합 인덱스에서는 열의 순서가 매우 중요하다. 인덱스 생성 순서에서 가장 왼쪽부터 열이 평가되기 때문이다. 따라서 이 경우 시간이 지나면서 점차 성능에 영향을 미치게 된다. 그러나 WHERE 절의 열을 선언하는 순서에는 이 같은 영향이 없다. 데이터베이스에 쿼리를 실행하기에 가장 좋은 방법으로 재구성하는 쿼리 계획 및 쿼리 옵티마이저와 같은 구성요소가 있기 때문이다. 이들 구성요소는 WHERE 절의 열을 재구성하고 순서를 변경할 수 있지만 여전히 인덱스의 열 순서에 의존한다.
정리하면 데이터 순서가 어느 부분에서 연산 및 인덱스에 영향을 미치는지를 아는 것이 중요하다. 그러면 전체적인 성능을 개선하고 설계를 최적화하기 위한 기회를 파악할 수 있다. 이를 위해서는 데이터와 연산자의 카디널리티(cardinality)가 매우 중요하다. 이 부분을 이해하면 설계를 더 개선하고 장기적인 가치를 끌어낼 수 있다.
언어 차이에 주의
SQL을 막 시작하는 개발자가 겪는 일반적인 문제 중 하나는 NULL과 관련된 문제다. 자바 개발자를 위해 자바 데이터베이스 커넥터(JDBC)는 애플리케이션을 데이터베이스에 연결하는 API를 제공한다. 단, JDBC는 SQL NULL을 자바 null에 매핑하지만 두 가지가 같지는 않다. SQL의 NULL 명령은 UNKNOWN이라고도 하는데, 이는 SQL NULL = NULL이 거짓이며 자바의 null == null과 같지 않음을 의미한다. 결과적으로, NULL을 사용한 산술 연산이 예상과 다른 결과를 도출할 수 있다. 이 불일치를 알면 애플리케이션의 한 요소를 데이터베이스 및 쿼리 설계로 변환하는 방법과 관련한 잠재적인 문제를 방지할 수 있다.
자바 및 데이터베이스와 관련해 피해야 하는 몇 가지 다른 패턴도 있다. 모두 연산이 수행되고 처리되는 방법 및 위치와 관련된 패턴이다. 예를 들어 개별적인 여러 쿼리에서 맵으로 테이블을 로드한 다음 처리를 위해 자바 메모리에서 조인할 수 있다. 그러나 이는 메모리에서 수행하기에 훨씬 더 까다롭고 계산 비용도 큰 방법이다. 대신 데이터베이스에서 처리가 가능하도록 수학적인 모든 요소를 정렬, 집계 또는 실행하는 방법이 더 낫다. 대부분의 경우 이런 쿼리 및 계산은 자바 메모리에서 처리하는 것보다 SQL로 작성하는 편이 더 쉽다.
데이터베이스에 맡기기
데이터베이스를 메모리에서 처리하면 구문 분석(parsing) 및 확인을 더 쉽게 해주고, 알고리즘보다 더 빠르게 계산을 수행할 수 있다. 하지만 이런 장점이 있다고 해서 꼭 그렇게 해야 한다는 의미는 아니다. 전체적인 속도를 이유로 그렇게 할 만한 가치는 없다. 다시 한 번 말하지만 인메모리 클라우드 서비스는 데이터베이스를 사용해 결과를 제공하는 방법에 비해 비용이 더 많이 든다.
페이지 매김도 마찬가지다. 페이지 매김은 쿼리 결과를 한 페이지가 아닌 여러 페이지에 걸쳐 정렬하고 표시하는 방법을 다루는데, 데이터베이스 또는 자바 메모리에서 처리할 수 있다. 수학적 연산과 마찬가지로 페이지 매김 결과도 메모리가 아닌 데이터베이스에서 수행해야 한다. 이유는 간단하다. 메모리 내의 각 연산은 모든 데이터를 메모리로 가져와서 트랜잭션을 수행한 다음 데이터베이스로 돌려보내야 하기 때문이다. 이 모든 과정이 네트워크를 통해 이뤄지면 실행될 때마다 왕복 이동이 추가되고 그에 따른 트랜잭션 지연도 추가된다. 이런 트랜잭션은 메모리에서 작업을 수행하는 것보다 데이터베이스를 사용하는 편이 훨씬 더 효율적이다.
또한 데이터베이스에는 연산의 효율성을 더욱 높일 수 있는 유용한 명령이 많다. LIMIT, OFFSET, TOP, START AT, FETCH와 같은 명령을 활용하면 현재 작업 중인 데이터 집합을 처리하는 방식을 중심으로 페이지 매김 요청의 효율성을 더 높일 수 있다. 마찬가지로, 조기 행 조회를 방지해 성능을 더 개선할 수 있다.
연결 풀링 사용
애플리케이션을 데이터베이스에 연결하려면 연결이 설정되고 트랜잭션이 수행되기 전에 작업이 필요하고 시간도 걸린다. 따라서 애플리케이션이 정기적으로 활성화되는 경우 이 작업이 오버헤드가 될 수 있다. 이에 대한 표준적 접근 방식은 연결 풀을 사용하는 것이다. 연결 풀에서는 트랜잭션이 필요할 때마다 연결을 여닫을 필요 없이 일정 시간 동안 연결 집합이 열린 상태로 유지된다. 이는 JDBC 3.0에서 표준화됐다.
이렇게 연결 풀링을 사용하는 시스템의 애플리케이션 성능은 이를 사용하지 않는 동일한 시스템에 비해 훨씬 더 높고, 전체적인 리소스 사용량은 낮다. 또한 연결 풀링은 연결 생성 시간을 줄이고 리소스 사용에 대한 더 폭넓은 통제력을 제공한다. 단, 애플리케이션과 데이터베이스 구성요소가 연결을 닫고 리소스 풀로 반환하는 부분에 관한 모든 JDBC 단계를 따르는지, 그리고 애플리케이션의 어느 요소가 실제 작동에서 이 부분을 담당하는지 확인하는 것이 중요하다.
배치 프로세스 활용
지금은 실시간 트랜잭션을 강조하는 경우가 많다. 고객 또는 비즈니스 요구에 대응하기 위해 전체 애플리케이션이 실시간으로 작동해야 한다고 믿는다. 하지만 꼭 그런 것은 아니다. 여러 트랜잭션을 처리하는 데 있어서 여러 INSERT 연산을 실행하는 방법보다 일괄 처리가 여전히 가장 일반적이고 가장 효율적인 방법일 수 있다.
특히 JDBC를 활용하면 큰 도움이 된다. JDBC는 일괄 처리를 이해하기 때문이다. 예를 들어 하나의 SQL 문과 여러 바인드 값 집합으로 일괄 INSERT를 만드는 것이 독립적인 여러 작업보다 더 효율적이다. 한 가지 유의해야 할 것은 성능에 영향을 미치지 않도록 트랜잭션이 많지 않은 시간 동안 데이터를 로드해야 한다는 것이다. 이것이 불가능한 상황이라면 대신 더 작은 규모의 일괄 작업을 정기적으로 실행하는 방법이 있다. 이렇게 하면 데이터베이스를 최신 상태로 유지하기 쉽고 트랜잭션 목록을 작게 유지하고 잠재적인 데이터베이스 잠금 또는 경쟁 조건을 피할 수 있다.
정리하면 SQL을 처음 시작하는 사람에게나 몇 년 동안 사용해 온 사람에게나 SQL은 여전히 미래를 위한 중요한 언어 기술이다. 여기서 살펴본 내용을 실무에 적용하면 애플리케이션 성능을 개선하고 SQL이 가진 이점을 활용할 수 있다.
editor@itworld.co.kr
VPN (가상 사설 네트워크, Virtual Private Network)은 인터넷 사용자에게 개인 정보 보호와 보안을 제공하는 중요한 도구로 널리 인정받고 있다. VPN은 공공 와이파이 환경에서도 데이터를 안전하게 전송할 수 있고, 개인 정보를 보호하는 데 도움을 준다. VPN 서비스의 수요가 증가하는 것도 같은 이유에서다.
동시에 유료와 무료 중 어떤 VPN을 선택해야 할지 많은 관심을 가지고 살펴보는 사용자가 많다. 가장 먼저 사용자의 관심을 끄는 것은 별도의 예산 부담이 없는 무료 VPN이지만, 그만큼의 한계도 있다.
무료 VPN, 정말 괜찮을까?
무료 VPN 서비스는 편리하고 경제적 부담도 없지만 고려할 점이 아예 없는 것은 아니다.
보안 우려
대부분의 무료 VPN 서비스는 유료 서비스에 비해 보안 수준이 낮을 수 있다. 일부 무료 VPN은 사용자 데이터를 수집해 광고주나 서드파티 업체에 판매하는 경우도 있다. 이러한 상황에서 개인 정보가 유출될 우려가 있다.
속도와 대역폭 제한
무료 VPN 서비스는 종종 속도와 대역폭에 제한을 생긴다. 따라서 사용자는 느린 인터넷 속도를 경험할 수 있으며, 높은 대역폭이 필요한 작업을 수행하는 데 제약을 받을 수 있다.
서비스 제한
무료 VPN 서비스는 종종 서버 위치가 적거나 특정 서비스 또는 웹사이트에 액세스하지 못하는 경우가 생긴다. 또한 사용자 수가 늘어나 서버 부하가 증가하면 서비스의 안정성이 저하될 수 있다.
광고 및 추적
일부 무료 VPN은 광고를 삽입하거나 사용자의 온라인 활동을 추적하여 광고주에게 판매할 수 있다. 이 경우 사용자가 광고를 보아야 하거나 개인 정보를 노출해야 할 수도 있다.
제한된 기능
무료 VPN은 유료 버전에 비해 기능이 제한될 수 있다. 예를 들어, 특정 프로토콜이나 고급 보안 기능을 지원하지 않는 경우가 그렇다.
유료 VPN의 필요성
최근 유행하는 로맨스 스캠은 인터넷 사기의 일종으로, 온라인 데이트나 소셜 미디어를 통해 가짜 프로필을 만들어 상대를 속이는 행위다. 이러한 상황에서 VPN은 사용자가 안전한 연결을 유지하고 사기 행위를 방지하는 데 도움이 된다. VPN을 통해 사용자는 상대방의 신원을 확인하고 의심스러운 활동을 감지할 수 있다.
그 외에도 유료 VPN만의 강점을 적극 이용해야 하는 이유는 다음 3가지로 요약할 수 있다.
보안 강화
해외 여행객이 증가함에 따라 공공 와이파이를 사용하는 경우가 늘어나고 있다. 그러나 공공 와이파이는 보안이 취약해 개인 정보를 노출할 위험이 있다. 따라서 VPN을 사용하여 데이터를 암호화하고 개인 정보를 보호하는 것이 중요하다. 서프샤크 VPN은 사용자의 개인 정보를 안전하게 유지하고 해킹을 방지하는 데 유용하다.
개인 정보 보호
인터넷 사용자의 검색 기록과 콘텐츠 소비 패턴은 플랫폼에 의해 추적될 수 있다. VPN을 사용하면 사용자의 IP 주소와 로그를 숨길 수 있으며, 개인 정보를 보호할 수 있다. 또한 VPN은 사용자의 위치를 숨기고 인터넷 활동을 익명으로 유지하는 데 도움이 된다.
지역 제한 해제
해외 여행 중에도 한국에서 송금이 필요한 경우가 생길 수 있다. 그러나 IP가 해외 주소이므로 은행 앱에 접근하는 것이 제한될 수 있다. VPN을 사용하면 지역 제한을 해제해 해외에서도 한국 인터넷 서비스를 이용할 수 있다. 따라서 해외에서도 안전하고 편리하게 인터넷을 이용할 수 있다.
빠르고 안전한 유료 VPN, 서프샤크 VPN
뛰어난 보안
서프샤크 VPN은 강력한 암호화 기술을 사용하여 사용자의 인터넷 연결을 안전하게 보호한다. 이는 사용자의 개인 정보와 데이터를 보호하고 외부 공격으로부터 사용자를 보호하는 데 도움이 된다.
다양한 서버 위치
서프샤크 VPN은 전 세계 곳곳에 여러 서버가 위치하고 있어, 사용자가 지역 제한된 콘텐츠에 액세스할 수 있다. 해외에서도 로컬 콘텐츠에 손쉽게 접근할 수 있음은 물론이다.
속도와 대역폭
서프샤크 VPN은 빠른 속도와 무제한 대역폭을 제공하여 사용자가 원활한 인터넷 경험을 누릴 수 있도록 지원한다. 온라인 게임, 스트리밍, 다운로드 등 대역폭이 필요한 활동에 이상적이다.
다양한 플랫폼 지원
서프샤크 VPN은 다양한 플랫폼 및 디바이스에서 사용할 수 있다. 윈도우, 맥OS, iOS, 안드로이드 등 다양한 운영체제 및 디바이스에서 호환되어 사용자가 어디서나 안전한 인터넷을 즐길 수 있다.
디바이스 무제한 연결
서프샤크 VPN은 무제한 연결을 제공하여 사용자가 필요할 때 언제든지 디바이스의 갯수에 상관없이 VPN을 사용할 수 있다.