프로젝트를 진행하다 보면 도메인간에 데이터를 주고 받는 경우가 많이 발생을 한다. 도메인간에 데이터를 주고 받을 때 .NET에서는 Serializable Attribute를 사용하여 객체를 직렬화해야만 한다. 그런데 간혹 데이터 사이즈가 너무 큰 경우 압축을 하고 싶은 경우가 있다. 이 경우 압축을 해서 데이터를 주고 받으면 약간의 효율이 좋을 수 있다. 이 부분은 닭이 먼저인지 달걀이 먼저 이겠지만 요즘같이 네트워크가 좋아진 상태에서 굳이 데이터를 압축하고 전송한 후 압축을 풀고 하는 과정을 시스템에 맡기는 것은 압축 하고 해제 하는 부분에서 또한 성능을 저해 할 수 있는 요소가 발생한다. 라고 하는 사람이 있을 것이고, 또 한 부류는 꺼꾸로 요즘 시스템의 가격이 저렴해지고, 시스템 성능은 많이 향상 되어 있는 상태에서 네트워크 트래픽을 줄이는 것이 더 효율적이라고 말하는 사람이 있을 것이다.
뭐가 됐던 간에 오늘은 도메인간의 데이터를 주고 받기 위해 객체를 압축하고 압축된 객체를 해제 하는 방법에 대해 알아 보도록 하겠다. 첫 번째의 경우야 그냥 데이터를 주고 받으면 그만 이기 때문에 보여줄 것이 없다.
.NET Framework 2.0 새로 추가된 GZipStream 클래스를 이용해 압축/해제를 할 수 있다. 이 클래스는 압축공개 알고리즘인 GZip file format specification 4.3 (http://www.ietf.org/rfc.html 에서 검색 할 수 있다.)을 이용해 만들어져 있다. 문제는 이 클래스만 이용해서는 Object를 압축 할 수 있지만 압축 되는 것처럼 객체의 사이즈가 줄어 든 것을 확인 할 수 있다. 이 것을 도메인간에 데이터를 넘긴 후 압축 해제를 시도 하면 압축 해제 할 때 헤더의 정보가 잘못 됐다는 둥 하면서 에러를 발생 시킨다. 그래서 MSDN 이곳 저곳을 찾아 봤지만 해결방법은 나와 있지 않다. 그래서 이리 저리 돌아 다니면서 확인한 결과 GZipStream을 가지고 압축을 한 후 헤더 정보를 만들어서 추가를 해야지만 해제를 할 때 그 헤더 정보를 이용해 압축을 해제 할 수 있다. 그 헤더의 정보는 압축 되기 전의 객체의 사이즈를 추가 하는 것이다. 이 것을 알아야 해제 할 때도 Steam 객체를 이용해 어디 까지 읽을 것인지를 결정할 수 있는 것이다. 아래 소스는 객체를 압축 하고 해제 하는 메소드를 구현한 내용이다.
참고로 GZipSteam 클래스를 이용해 압축 한 후 파일로 쓰는 것은 특별의 헤더 정보를 추가 하지 않아도 된다. 해제 할 때 도 마찬가지 이다. 이 경우는 메모리의 데이터를 압축해서 그 데이터를 전송한 후 해제 할 때만 해당 되는 내용이다.
- 압축 하기 메소드
2. 압축 해제 하기 메소드
2009년 1월 6일 조금 있다가 외근을 준비 하면서 오늘 춥네요 ^^ .NETer