RPC Framework: Apache Thrift

카카오톡 서버와 API를 연동할 일이 있었다. REST로 구현할 생각을 하고 있었다. Apache Thrift로 되어 있었는데, Thrift에 대해 막연히 알고는 있었으나 한 번도 구현해본 적이 없어 어느정도 어려움이 있을지 예측이 안되는 상태였다. 게다가 Go 또는 C++로 바인딩 해야 했는데 해당 언어는 wrapper를 구현해두지 않은 상태라 작업 일정 또한 예측이 어려웠다. 차일피일 미루다 결국 서비스 전략에 변화가 생기며 연동 작업은 없던 일이 되고 말았다. 마음 한 켠에 못내 '기술 부채(Technical Debt)'로 남아 있다 얼마전 『Learning Apache Thrift, 2015』를 읽은 계기로 언젠가는 다시 연동할 일이 있을거란 생각에 직접 C++과 Python으로 실습을 진행해보고 기록을 남긴다.

2019년 7월 30일 문서 복원
2017년 7월 4일 초안 작성

서론

CORBA, DCOM, Java-RMI, .NET Remoting, ZeroC’s ICE와 같은 대표적인 RPC 모델들은, 분산 컴퓨팅은 로컬 컴퓨팅과 근본적으로 다른데 이러한 차이점을 감안하지 않고, 로컬과 동일한 방식으로 원격 호출을 수행하려는 한계를 지닌다.

  • Apache Thrift is an interface definition language and binary communication protocol that is used to define and create services for numerous languages. It is used as a remote procedure call (RPC) framework and was developed at Facebook for “scalable cross-language services development”.
  • gRPC is high performance RPC framework that uses Protocol Buffers.
    • Protocol Buffers: Protocol buffers are Google’s language-neutral, platform-neutral, extensible mechanism for serializing structured data.

『Learning Apache Thrift, 2015』의 챕터 7. An Example Client-Server Application을 실습 해봤으나 thrift EOFError readall()가 발생했고 검색 해봐도 비슷한 유형의 문제를 겪은 사례를 찾기 힘들었다. 버전 차이로 인한 문제로 보였으나 아쉽게 해결하지 못해 공식 사이트의 튜토리얼로 다시 실습했다.

구현

Python

맥에서는 brew로 설치했다. 그러나 C++에서는 코드 실행을 위한 lib가 필요하므로 소스를 직접 받아서 프로젝트 디렉토리에 두어야 한다.

thrift -r --gen py tutorial.thrift

파이썬 샘플

실행 결과

C++

C++ 가이드에는 빌드 방법이 따로 없어 CMake로 빌드를 진행해보았다. C++11 버전으로 설정해야 error: no member named 'bind' in namespace 'std'; 오류가 발생하지 않으며, gen-cpp의 소스까지 모두 빌드해야 한다. -lthrift 플래그를 설정하지 않으면 ld: symbol(s) not found for architecture x86_64 심볼을 찾지 못한다. brew로 설치했다면 /usr/local/include에 thrift header가, /usr/local/lib에 동적 라이브러리(dylib)가 이미 들어있다. skeleton을 빌드에서 제외한 CMakeLists.txt의 전체 내용은 아래와 같다.

cmake_minimum_required(VERSION 3.7)
project(thrift_official)

set(CMAKE_CXX_STANDARD 11)

set(SOURCE_FILES
        cpp/CppServer.cpp
        gen-cpp/Calculator.cpp
        gen-cpp/Calculator.h
        gen-cpp/shared_constants.cpp
        gen-cpp/shared_constants.h
        gen-cpp/shared_types.cpp
        gen-cpp/shared_types.h
        gen-cpp/SharedService.cpp
        gen-cpp/SharedService.h
        gen-cpp/tutorial_constants.cpp
        gen-cpp/tutorial_constants.h
        gen-cpp/tutorial_types.cpp
        gen-cpp/tutorial_types.h
        )

add_executable(thrift_official ${SOURCE_FILES})

set(LDFLAGS "-lthrift")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${LDFLAGS}")

실행 결과

$ ./thrift_official 
Starting the server...
Incoming connection
        SocketInfo: <Host: ::1 Port: 60233>
        PeerHost: localhost
        PeerAddress: ::1
        PeerPort: 60233

기타

CLion에서는 소스 파일이 비활성화 되는 문제가 있었는데, CMakeLists.txt를 임의로 만들어주고 프로젝트(.idea 디렉토리)를 삭제했다가 다시 오픈하니 잘 인식한다. 애초에 CMakeLists.txt가 없을때 imports로 열었는데, 이후에 파일을 만들었지만 자동으로 인식하지 못했다.

is a collection of Papers I have written.
© 2000 - Sang-Kil Park Except where otherwise noted, content on this site is licensed under a CC BY 4.0.
This site design was brought from Distill.