백엔드

Apache Ignite에 대해 알아보자 - (1)개념 이해

CyberI 2017. 12. 13. 16:21

 

 

 

Apache Ignite는 인메모리 컴퓨팅 플랫폼(in-memory computing platform)으로 데이터 레이어와 사용자 애플리케이션 레이어 사이에 완벽하게 들어갈 수 있습니다. 기존의 디스크 기반 저장소 레이어로부터 RAM으로 데이터를 로드하여, 최대 6자리수(백만배)까지 성능을 향상시킬 수 있습니다. 클러스터에 노드를 추가하기 만하면 인메모리 데이터 용량(in-memory data capacity)을 쉽게 확장하여 페타 바이트 단위의 데이터를 처리 할 수 있습니다. 또한 기존에 사용하는 데이터베이스를 전면 교체할 필요가 없으며, RDBMS, NoSQL, 하둡 데이터 저장소와 함께 잘 작동합니다. 따라서 대용량 데이터를 높은 성능으로 빠르게 처리해야 하는 시스템에 도입을 고려해볼 수 있습니다.

1. 알아야 하는 개념

1) Persistent Storage

'Persistent Storage'를 말 그대로 보자면 'Persistent'는 '오래 지속되는, 영구적인'이라는 뜻이 있고 'Storage'는 저장소이기 때문에 '오래 지속되는/영구적인 저장소'라고 할 수 있습니다. 한국어의 정확한 명칭이 궁금해서 찾아봤는데, 사용되는 곳마다 '영구 저장소, 장기보관 스토리지, 지속적 저장소, 영속적 저장소' 등으로 다양했습니다. 사실 조금씩 느낌이 다른 단어들이고, 명확하게 정해진 것이 없지만 이 포스트에서는 저장소에서 데이터가 '계속 지속되며 변함이 없다'는 데에 의미를 두어 '영구 저장소'라고 칭하겠습니다. 

영구 저장소(Persistent storage)는 장치의 전원이 꺼진 후에도 데이터를 유지하는 모든 데이터 저장소 장치입니다. 가끔 비휘발성(non-volatile) 저장소라고 일컬어집니다. HDD와 SSD는 영구 저장소의 가장 일반적인 타입입니다. 반면, RAM과 캐시(cache)는 전형적인 비영구 저장소(Non-persistent storage)로, 전원을 끄면 데이터는 지워집니다. 그러나, 비휘발성 RAM이나 플래시기반의(flash-based) RAM은 지속성이 있습니다. 지속성은 충돌이나 리부팅을 했을 때, 데이터가 상실되지 않는다는 이점이 있습니다.

2) In-memory Database

'In-memory Storage'는 컴퓨터의 메인 메모리에 데이터를 저장하는 저장소입니다. 디스크에 저장된 데이터에 접근하는 것보다 더 빠른 시간내에 데이터에 접근할 수 있습니다. 그렇기 때문에 데이터를 조회할 때 시간이 단축되며 더 나은 성능을 기대할 수 있습니다. 인메모리 저장소는 RAM이 휘발성이기 때문에, 장치의 전원이 나가거나 리부팅이 될 때 휘발성 RAM에 저장된 데이터가 날라간다는 기술적인 한계가 있었습니다. 그러나 비휘발성 RAM 기술의 등장으로 이런 단점을 극복하고 있습니다.

'In-memory Database'(IMDB)는 컴퓨터의 데이터 저장을 위해 메인 메모리에 주로 의존하는 DBMS(Database Management System)입니다. 디스크 저장 메커니즘을 사용하는 DBMS보다 데이터 조회 시 탐색 시간이 짧고 디스크에 액세스(access)하는 것보다 메모리에 액세스하는 것이 더 빨라서 통신 네트워크 장비, 모바일 광고 네트워크를 실행하는 등 응답시간이 중요한 애플리케이션에서 주로 사용됩니다.

메인 메모리 데이터베이스는 휘발성 메모리 장치에 데이터를저장합니다. 이 장치는 전원이 나가거나 리셋될 때 저장된 모든 데이터를 상실합니다. 이 경우 IMDB는 데이터베이스 트랜잭션이 보증해야할 ACID(atomicity, consistency, isolation, durability; 원자성, 일관성, 고립성, 지속성) 속성 중 '지속성(durability)'에 대한 지원이 부족하다고 할 수 있습니다. 휘발성 메모리 베이스 IMDB는 다른 세 가지 속성을 대체로 지원을 할 수 있으며 많은 IMDB들이 스냅샷 파일, 체크포인트 이미지, 트랜잭션 로깅, 비휘발성 메모리, 데이터베이스 복제와 같은 메커니즘을 통해 지속성을 보장합니다.

2. Apach Ignite란?

Apache Ignite는 강력한 SQL, key-value 그리고 프로세싱 API를 가진 지속성이 있고(durable), 강력하게 일관성을 유지하는(strongly consistent) 고가용성(highly available)의 인메모리 컴퓨팅 플랫폼입니다. Ignite는 Native persistence기능을 껐다 켜는 것만으로 퍼시스턴트 스토리지가 될 수도 순수한 인메모리 스토리지가 될 수도 있습니다. 또한 Ignite의 데이터는 다수 노드의 클러스터를 통해 파티션되거나(partitioned) 복제될(replicated) 수 있는 분산 데이터베이스입니다.

Ignite가 SQL을 지원하기는 하지만 완전한 관계형 SQL 데이터베이스라고 할 수는 없습니다. 관계형 SQL데이터베이스처럼 동작하는 것을 지향하면서도, 제약조건이나 인덱스를 처리하는 데에 있어 약간의 차이점이 있기 때문입니다. Ignite는 primary와 secondary 인덱스를 지원하지만, 고유성(uniqueness)은 primary 인덱스에만 강제할 수 있습니다. 또한 Ignite는 외래키 제약조건을 지원하지 않습니다. 본질적으로, Ignite는 의도적으로 각 업데이트에 대한 클러스터 브로드캐스트 메시지(cluster broadcast message)를 수반하거나 심각하게 시스템의 확장성 및 성능에 악영향을 주는 어떤 제약조건도 지원하지 않습니다.

3. Apache Ignite 주요특징

1) 지속되는 메모리(durable memory)

Ignite의 지속되는 메모리 컴포넌트(durable memory component)는 RAM을 단지 캐싱 레이어(caching layer)가 아니라 모든 기능을 완전히 하는 저장 레이어(storage layer)로 다룹니다. 이는 사용자가 필요에 따라 persistence를 켜거나 끌 수 있다는 것을 의미합니다. 즉, Ignite는 persistence의 on/off 상태에 따라서 영구 저장소(persistent storage)될 수도 순수하게 인메모리 저장소(in-memory storage)가 될 수도 있습니다.

만약 persistence가 꺼져있다면, Ignite는 순수한 인메모리 저장소가 되며 SQL와 key-value API중 어떤 것을 사용하기를 선호하는 지에 따라서 분산된 인메모리 데이터베이스(IMDB)나 인메모리 데이터 그리드(IMDG) 역할을 합니다.

만약 persistence가 켜져 있다면, Ignite는 *메모리 중심적*인 시스템처럼 기능하기 시작하는데, 프로세싱의 대부분이 메모리에서 일어나지만 데이터와 인덱스는 디스크에 보관됩니다. 또한 모든 데이터의 일관성을 보장하고 모든 클러스터(cluster) 실패에 대해 회복력이 있는 분산되고 수평적으로 확장가능한 데이터베이스가 됩니다. 여기서 전통적인 디스크 중심 RDBMS나 NoSQL 시스템과 크게 다른 점은 Ignite는 강력히 일관되고, 수평적으로 확장가능하며, SQL과 key-value 처리 API를 지원한다는 점입니다. 

Apache Ignite는 Ignite Native Persistence가 가능할 때 데이터와 인덱스를 저장하고 처리하는 것을 메모리와 디스크에서 둘 다 할 수 있게 하는 '지속되는 메모리' 아키텍쳐에 기반을 두고 있습니다. '지속되는 메모리' 아키텍처는 디스크 지속성(durability)과 한 시스템에서의 강력한 일관성과 함께 인메모리 컴퓨팅의 성능과 규모를 달성하는 데 도움이 됩니다.

Ignite의 지속되는 메모리는 리눅스같은 운영 시스템의 가상 메모리와 유사한 방식으로 작동합니다. 그러나, 이 둘의 한 가지 큰 차이점은 지속되는 메모리는 전체 혹은 부분적인 데이터 셋을 메모리에 보관하는 데다가, 항상 디스크상에 인덱스를 포함한 전체 데이터 셋을 유지하는 반면, 가상 메모리는 RAM이 부족할 때 교환의 목적으로만 디스크를 사용합니다.

*메모리 중심적(memory centric): Ignite는 디스크 지속성과 한 시스템 내에서의 강력한 일관성과 함께 성능과 인메모리 컴퓨팅의 규모를 결합한 메모리 중심적 아키텍처를 기반으로 합니다. 메모리 중심적인 접근과 전통적인 디스크 중심적인 접근의 가장 큰 차이점은 메모리를 완전히 기능하는 저장소로 다루는지 아니면 단지 대부분의 데이터베이스들이 그렇듯이 caching 레이어로 다루는지 입니다. Ignite는 순수한 인메모리 모드에서 기능을 수행할 수 있으며, 이 경우 인메모리 데이터베이스(IMDB)나 인메모리 데이터 그리드(IMDG)처럼 다뤄질 수 있습니다.

2) Ignite Native Persistence

Ignite native persistence는 ACID(Atomicity, Consistency, Isolation, Durability - 원자성, 일관성, 고립성, 지속성) 속성을 가지며,  SQL 호환성이 있는 분산 디스크 저장소로 Ignite의 '지속되는 메모리'와 함께 투명하게 통합할 수 있습니다. Ignite persistence는 부가적이며 껐다 켰다할 수 있습니다. 꺼져있을 때, Ignite는 순수하게 인메모리 저장소가 됩니다.

가능한 native persistence와 함께, Ignite는 항상 디스크와 가능한만큼의 RAM에 데이터의 상위집합(superset)을 저장합니다. 예를 들어, 100개의 엔트리가 있고 RAM이 오직 20개를 저장할 수 있는 용량을 가지고 있다면, 100개 모두 디스크상에 저장되며 오직 20개만 더 나은 성능을 위해서 RAM에 캐싱됩니다.

native persistence는 다음과 같은 중요한 특징이 있습니다.

  • 메모리와 디스크 양쪽에 걸쳐있는 모든 데이터 셋에 대한 SQL 쿼리. 이는 Apache Ignite가 메모리 중심의 분산된 SQL 데이터베이스처럼 사용될 수 있다는 것을 의미합니다.
  • 메모리에 모든 데이터를 가지고 있을 필요가 없습니다. Ignite persistence는 데이터의 상위 집합을 디스크에 저장하고 오직 가장 빈번하게 하용되는 하위 집합(subset)만 메모리에 저장하도록 합니다.
  • 즉각적인 클러스터 재시작. Ignite는 클러스터가 시작 혹은 재시작하면 즉시 디스크로부터 완전히 작동하게 됩니다. 미리 로드하거나 인메모리 캐시에서 준비를 할 필요가 없습니다. 데이터가 액세스되면 데이터는 인메모리에 천천히 로드됩니다.
  • 데이터와 인덱스는 메모리와 디스크 양쪽에 비슷한 포맷으로 저장됩니다. 이는 메모리와 디스크 간 데이터를 이동할 때 발생하는 값비싼 변형작업을 피할 수 있게 도와줍니다.
  • third party 솔루션을 플러그인으로 사용하여 전체 혹은 증가하는 클러스터 스냅샷을 생성할 수 있는 기능이 있습니다.

Write-Ahead 로그: 데이터가 메모리에 업데이트될 때마다, 업데이트 작업은 미리쓰기로그(write-ahead log;WAL) 의 끝(tail)에 붙습니다. WAL의 목적은 가능하면 가장 빠른 방법으로 디스크에 업데이트를 전파하고 전체 클러스터 실패를 지원하는 일관된 복구 매커니즘을 제공하는 것입니다.

전체 WAL은 연속하여 채워지는 세그먼트(segment)라고 불리는 몇개의 파일로 나뉘어집니다. 하나의 세그먼트가 다 차면, 컨텐트는 WAL 아카이브에 복사되어 설정 가능한 시간 동안 보존될 것입니다. 세그먼트가 복사되는 동안, 다른 세그먼트가 활성화된 WAL 파일로 취급됩니다.

클러스터는 언제나 가장 최근에 커밋이 성공된 트랜젝션의 상태로 복구될 수 있습니다.

checkpointing: WAL이 커짐에 따라, 주기적으로 메인 저장소에 체크포인트됩니다(checkpointed). 체크포인팅이란 메모리로부터 디스크의 파티션 파일로 'dirty page'를 복사하는 프로세스입니다. dirty page란 메모리에서 업데이트가 되어 WAL에는 추가되었지만, 디스크의 각각의 파티션 파일에는 아직 쓰이지 않은 페이지를 의미합니다. 

3) 분산 SQL 데이터베이스

Ignite는 ANSI-99와 호환되며, 수평적으로 확장 가능한 고장 방지의(fault-tolerant) 분산 SQL 데이터베이스를 함께 제공합니다. 사용 환경에 따라 클러스터 노드를 통해 데이터를 분할함으로써 혹은 전체 복제(full replication)를 함으로써 분배할 수 있습니다. 다른 분산 SQL 데이터베이스와 달리, Ignite durable memory는 활성화된 저장소 계층(tier)으로 메모리와 디스크 둘 다 취급합니다. native persistence로 알려진 디스크 계층은 기본적으로 비활성화되어있으며, 이 경우 Ignite는 순수한 인메모리 데이터베이스가 됩니다.

표준 JDBC 또는 ODBC 연결을 사용하여 다른 SQL 스토리지와 마찬가지로 Ignite와 상호 작용할 수 있습니다. Ignite는 또한 Java, .NET, C++ 개발자에게 더 나은 성능을 위한 native SQL API를 제공합니다.

Ignite의 구별되는 특징들 중 하나는 분산 SQL JOIN을 위한 완전한 지원입니다. Ignite는 배치된(collocated) 혹은 그렇지 않은 방식으로 데이터를 join할 수 있습니다. 배치되었을 때, 네트워크를 통해 큰 데이터 셋을 옮길 필요없이 각 노드에서 가능한 로컬 데이터에서 실행됩니다. 이러한 접근법은 분산 데이터베이스에서 최고의 확장성과 성능을 제공합니다.

collocated processing(배치 처리): RDBMS 혹은 NoSQL처럼 디스크 중심적인 시스템은 일반적으로 클라이언트-서버 방식으로 작동하는데, 이 전통적인 클라이언트-서버 접근법은 데이터가 서버로부터 클라이언트 사이드로 전달되고 여기서 데이터가 처리되며 그런 후 보통은 폐기됩니다. 이 접근법은 규모를 잘 확장하지 않는데 네트워크 상으로 데이터를 이동하는 것이 분산 시스템에서 가장 비용이 많이 드는(expensive) 작업이기 때문입니다.

보다 확장 가능한 접근법은 데이터가 실제로 존재하는 서버쪽으로 계산(computations)을 가져옴으로써 흐름을 역전시킨 배치 처리(collocated processing)입니다. 이 접근법은 값비싼 직렬화나 네트워크 이동을 피하면서 데이터가 저장된 위치에서 고급 로직이나 JOIN을 포함한 분산 SQL을 실행하게 해줍니다.

예를 들어, 뉴욕에 눈보라가 쳐서 약 8만명에게 경보 문자 메시지를 보낸다고 가정해보겠습니다. 8만건의 정보를 데이터베이스에서 문자메시지 애플리케이션으로 가져오는 것이 아니라, 문자메시지 로직을 뉴욕거주자 정보를 담고있는 클러스터 노드로 보냅니다. 결과적으로 8만건의 정보를 네트워크로 전송하는 대신 1개의 계산만 이동하게 되어 퍼포먼스가 훨씬 좋습니다.

4) 인메모리 데이터 그리드(In-Memory Data Grid)

Ignite 인메모리 데이터 그리드는 처음부터 수평적인 규모(horizontal scale)의 개념과 실시간으로 필요할 때 노드를 추가할 수 있는 능력을 바탕으로 만들어졌습니다. 데이터그리드는 *데이터 로컬리티(data locality)*와 불필요한 데이터 잡음(data noise)을 줄이기 위한 관련성 데이터 라우팅(affinity data routing)을 위해 강력한 시맨틱을 가지고 선형적으로 수백개의 노드로 확장할 수 있게 설계되었습니다.

Ignite 데이터 그리드는 인메모리 분산 key-value 저장소로 전체 데이터의 일부를 소유하고 있는 모든 클러스터 노드를 분산된 분할 해시맵으로 볼 수 있습니다. 이렇게하면 더 많은 클러스터 노드를 추가할수록 더 많은 데이터를 캐시할 수 있습니다. 다른 key-value 저장소와는 다르게, Ignite는 장착형 해싱 알고리즘(pluggable hashing algorithm)을 사용하여 데이터 로컬리티를 결정합니다. 모든 클라이언트는 해싱 함수에 키를 연결함으로써 별도의 매핑 서버나 네임 노드(name nodes)를 필요로 하지 않고, 어떤 노드에 키를 속하게 할 지 결정할 수 있습니다.

또한 Ignite 데이터 그리드는 분산 트랜잭션 key-value 저장소로, 다른 인메모리 데이터 그리드와 다르게 Ignite는 데이터를 메모리와 디스크 둘 다에 저장할 수 있게 합니다. 표준 key-value 데이터 동작 외에, ACID 트랜잭션과 모든 JCache 기능을 포함하며, 또한 데이터에 대해 분산 조인과 더불어 SQL 쿼리를 지원합니다.

Ignite 데이터 그리드는 현재 분산 클러스터에서 ACID 트랜잭션 또는 원자 데이터 업데이트를 가장 빠르게 구현한 것 중 하나입니다. 데이터 그리드에 있는 데이터는 순수하게 메모리에 저장될 수도, 디스크에서 지속될 수도 있습니다. 만약 Ignite native persistence가 가능하면, 데이터와 인덱스는 모든 클러스터 노드에 기본적으로 유지됩니다. 이 경우, 메모리는 오직 전체 유지되는 데이터 셋의 작은 캐싱 레이어와 같은 역할을 합니다. 모든 쿼리와 트랜잭션은 디스크에 저장된 전체 데이터셋에 걸쳐있습니다.

인메모리 데이터 그리드는 또한 RDBMS와 NoSQL, 하둡 기반의 저장소과 같은 3rd party 데이터베이스와 함께 통합함으로써 성능과 확장 가능성을 향상시킵니다. 이 접근법은 기존 데이터의 전면적인 교체를 요구하지 않지만, 한계를 가지고 있습니다. 예를 들어, SQL 혹은 검색 쿼리(scan queries)는 Ignite가 외부 데이터에 대한 어떤 지식도 없기 때문에 외부 데이터베이스가 아니라 오직 메모리에 저장된 결과만을 포함합니다. 

*데이터 로컬리티(data locality): 큰 데이터를 계산하는 쪽으로 이동시키는 대신, 실제 데이터가 존재하는 노드쪽으로 계산을 보내는 능력을 의미합니다. (참조링크)

5) 클러스터링(clustering)

Ignite는 논리적 클러스터 그룹과 자동 발견(auto-discovery)를 포함한 향상된 클러스터링 능력을 가지고 있습니다. Ignite의 노드는 자동적으로 서로 발견할 수 있습니다. 이는 필요할 때 전체 클러스터의 재시작 없이 클러스터의 규모를 확장하는 데에 도움을 줍니다. 개발자는 또한 Ignite의 개인 클라우드(private clouds)와 아마존 웹 서비스와 같은 공용 클라우드(public clouds) 간 연결을 구축하게 해주는 하이브리드 클라우드를 활용하여, 각각의 장점을 모두 제공할 수 있습니다.

4. Ignite 라이프사이클

Ignite는 JVM기반입니다. 하나의 JVM은 하나의 혹은 다수의 논리적인 Ignite 노드를 나타냅니다. (그러나, 대부분의 경우 하나의 JVM이 하나의 Ignite 노드를 실행합니다.) Ignite 문서 처음부터 끝까지, 용어 'Ignite runtime'과 'Ignite node'를 대부분 교환 가능하게 사용하였습니다. 예를 들어, "이 호스트에서 5개의 노드를 실행할 수 있다"고 말한다면, 대부분의 경우 이것은 기술적으로 호스트에서 각각 하나의 Ignite 노드를 실행하는 5개의 JVM을 시작할 수 있다는 것을 의미합니다. Ignite는 또한 하나의 JVM에서 다수의 노드를 지원합니다. 사실, Ignite에 대한 대부분의 내부 테스트를 그 방식으로 실행합니다.

1) Ignition 클래스

Ignition 클래스는 네트워크 토폴로지(network topology)에서 개개의 Ignite 노드를 시작합니다. (네트워크 상의 컴퓨터와 같은) 물리적인 서버는 그 위에서 실행하는 다수의 Ignite 노드를 가질 수 있습니다. 모든 설정을 default로 하고 그리드 노드를 논리적으로 실행하는 방법은 Java 코드로 다음과 같습니다.

Ignite ignite = Ignition.start();

혹은 설정 파일의 경로를 파라미터로 넘겨서 시작할 수도 있습니다. 경로는 절대경로가 될 수도 있고 IGNITE_HOME 혹은 클래스패스의 META-INF 폴더의 상대경로가 될 수도 있습니다.

2) 라이프사이클빈(LifecycleBean)

때로는 Ignite노드를 시작하거나 멈출 때 특정한 액션을 수행해야 하는 경우가 있습니다. 이는 LifecycleBean 인터페이스를 구현함으로써 가능하며, 스프링 XML 파일에서 IgniteConfiguration의 lifecycleBeans property에서 구현한 bean을 구체화할 수 있습니다.

<bean class="org.apache.ignite.IgniteConfiguration">
    ...
    <property name="lifecycleBeans">
        <list>
            <bean class="com.mycompany.MyLifecycleBean"/>
        </list>
    </property>
    ...
</bean>

또한 프로그래밍적으로 LifeCycleBean을 설정할 수도 있습니다.

Apache Ignite에 대해 간단하게 개념과 특징에 대해 살펴보았습니다. 내용은 https://ignite.apache.org 사이트와 https://apacheignite.readme.io/docs/ 사이트를 참조하였습니다. 제가 쓴 내용 외에 더 많은 특징에 대한 자세한 설명은 하단에 명시한 사이트에서 보실 수 있습니다. 맨 아래 링크를 건 페이지에서는 Apache Ignite에 대한 설명, 주요 특징, 설계에 대해 자세히 잘 정리된 글(영문)이니 읽어보시면 많은 도움이 될 것 같습니다. 그리고 다음 포스팅에서는 실제로 테스트를 해보는 내용을 올릴 예정입니다.

* 참조사이트

https://ignite.apache.org/features/durablememory.html

https://apacheignite.readme.io/docs/ignite-facts

https://www.infoworld.com/article/3135070/data-center/fire-up-big-data-processing-with-apache-ignite.html

 


Apache Ignite에 대한 더 자세한 내용을 살펴보고 싶다면, 아래 링크를 클릭해주세요.

▶ Apache Ignite에 대해 알아보자 - (2)설치 및 실행

 

사이버이메지네이션 회사 소개