2016. 7. 22. 11:10 Network

FlatBuffers Guide

https://google.github.io/flatbuffers/


FlatBuffers Documentation


flatbuffers는 효율적인 크로스 플랫폼 직렬화 라이브러리이다.

C++, C#, C, Go, Java, JavaScript, PHP, Python을 지원한다.


이건 원래 구글이 게임 개발과 또다른 성능이 치명적인 프로그램을 위해 만들어졌다.


이것은 아파치 라이센스 v2 기반의 github 오픈소스로써 사용 가능하다.


왜 Flatbuffers를 쓰는가?

  • parsing이나, unpacking 전에도, 직렬화 데이터에 접근 가능하다.

  • 메모리가 효율이 좋고, 빠르다.

  • 유연하다.

  • 경량 코드

  • 강한 타입 처리

  • 편리한 사용

  • 종속성 없는 크로스 플랫폼 코드


https://google.github.io/flatbuffers/flatbuffers_guide_writing_schema.html


writing a schema

C계열 언어 사용자들과 또 다른 언어 사용자들에게 또한 친숙한 스키마 언어 문법으로 작성된다.


// example IDL file

namespace MyGame;

attribute "priority";

enum Color : byte { Red = 1, Green, Blue }

union Any { Monster, Weapon, Pickup }

struct Vec3 {
 x:float;
 y:float;
 z:float;
}

table Monster {
 pos:Vec3;
 mana:short = 150;
 hp:short = 100;
 name:string;
 friendly:bool = false (deprecated, priority: 1);
 inventory:[ubyte];
 color:Color = Blue;
 test:Any;
}

root_type Monster;

(Weapon & Pickup not defined as part of this example)

Tables

테이블은 flatbuffers의 오브젝트를 정의하는 주된 방법이고, 이름과 필드 목록을 가지고 있다.


각 필드는 이름, 타입, 선택 사항으로 기본 값을 가진다.


각 필드의 선택 사항 : 이건 반드시 표현 할 필요는 없다, 그리고 당신은 개별 필드 누락을 선택 할 수 있다.


결과 같이, 당신은 유연하게 데이터의 팽창을 두려워하지 않고, 필드를 추가해도 된다.


이 디자인은 flatbuffers의 메커니즘의 전방위적, 배경적 호환성을 위함 이기도 하다.


Note that:

  • 새 필드는 스키마의 테이블 정의 끝에 추가할 수 있다. 오래된 데이터는 아직 정확히 읽을 수 있고, 그리고 당신은 읽을 때의 기본 값을 줄 수 있다.
    오래된 코드는 단순하게 새 필드를 무시 할 수 있다.
    만일 당신이 유연성을 원한다면, 특정 순서 보장을 원한다면, 수동으로 대입 (protbuf와 매우 유사), id 속성 아래를 봐라.

  • 당신은 최신 스키마로부터 필드를 삭제를 할 수 없다, 그러나 단순하게 당신의 그 곳에 데이터를 기록하는 걸 멈추는 것과 거의 비슷한 효과를 낼 수 있다. 위의 예제를 보면 부가적으로 당신은 그 곳에 deprecated  마크를 할 수 있고,  C++로 생성 되어 있던 접근자들로부터  보호 될 거고, 필드가 더 이상 사용되지 않는 것으로 시행하는 방법이다. (조심해 : 이건 깨질 수 있는 코드야!)

  • 이름이 변경 된 것들과 원래와 같은 때 까지 코드가 깨지는지 확인한다면, 필드 이름과 테이블 이름을 바꿀 수 있어.


밑에 스키마 진화 예제를 확인하자~


Structs

테이블과 유사하고, 오직 현재 비어있는 필드는 선택적이고 (그래서 디폴트 없음 쪽이나), 그리고 필드는 추가하지 못하거나, deprecated일 것이다.

Structs는 오직 수치형 자료나 또 다른 Structs만을 포함 할 수 있다.


단순한 자료형이나, 매우 확정 적으로 영원히 안 바뀔 것들을 만들 때 써라. ( 꽤 분명한 예는 Vec3)


Structs는 table보다 적은 메모리를 사용하고, 빠른 접근도 가능하다. (그것은 항상 그들의 부모 오브젝트에서 in-line되고, 가상 테이블을 사용하지 않는다)


Types

내장 수치 타입

  • 8bit : byte, ubyte, bool

  • 16bit : short, ushort

  • 32bit : int, uint, float

  • 64bit : long, ulong, double


내장 비-수치 타입

  • 다른 타입의 Vector, 계층화 된 벡터는 지원하지 않고, 대신 당신은 테이블안에 내부 벡터로 감쌀 수 있다.

  • string, UTF-8이나 7-bit ASCII로 고정되어 있다. 다른 텍스트 인코딩 또는 일반 바이너리 데이터는 벡터([byte] or [ubyte])로 대체 할 수 있다.

  • 또다른 tables나 structs, enums, unions 참고해라. (밑을 보시오)


필드 타입은 한번 사용되고 나면 바꿀 수 없다, 예외적으로 같은 사이즈 데이터에 reinterpret_cast를 사용하면 원하는 결과를 얻을 수 있다, 예를 들어 현재 사용되고 있던 최상위 비트 값이 없는 경우 uint를 int로 바꿀 수 있다.


https://google.github.io/flatbuffers/md__cpp_usage.html


'Network' 카테고리의 다른 글

FlatBuffers Guide  (0) 2016.07.22
동기화에 대한 간략 정리  (0) 2016.06.30
로직의 네트워크 동기화 처리  (0) 2015.01.28
TCP/IP, UDP 주요 포트  (0) 2013.03.22
ncftp 사용법  (0) 2011.02.17
FTP Passive / Active 모드  (0) 2011.02.17
Posted by 엘키 엘키

댓글을 달아 주세요

오늘은 많은 서버 개발자 분들이 (그리고 더 많은 다른 파트 개발자 분들이) 알고 계신데 막상 개발 플랜에 누락되는 일이 비일비재한 것들에 대해 이야기 해보고자 합니다.

많은 팀이 겪게되는 가상 시나리오를 그려보겠습니다.


--------------------------------------------------------------------------------------------

프로토타이핑이 성공적이었습니다!

개발팀이 세팅 됩니다.


개발 언어, 플랫폼, 엔진 (or 프레임워크)등을 정하게 되죠.


베이스 작업 기간으로 한달 정도 잡습니다.


컨텐츠별로 1주~2주 사이를 잡습니다.

그리고 각 컨텐츠가 다 완성되고 폴리싱 작업으로 한달 잡네요.


네. 좋습니다.


대략 컨텐츠가 8개 정도 되네요.


평이한 컨텐츠가 다수라 8주라 예상해봅시다.



베이스 작업+컨텐츠해서 3달 나왔네요.

폴리싱까지 4달이었죠?


여유 기간 포함해서 5달 질러봅니다.

오오!! 승인됐네요.


자~ 작업에 들어갑니다.

베이스 작업은 예상대로 잘 됩니다. 오히려 시간이 조금 남았네요?


작은 오차들과 예상외 변수가 있었지만 그럭저럭 개발 기간을 맞췄군요!


기능도 오류가 좀 있지만, 폴리싱 기간에 집중하면 될거 같은 양입니다.

출시 문제 없겠네요. 하하하~


… 헌데… 예상치 못한 일들이 끼어들어오기 시작합니다.

GM툴과 사용법을 달라고 하시는군요.


… 헐...꼭 해줘야할까…? 고민도 되고 반려도 하고 싶지만, 서비스를 위해 꼭 필요한 기능이죠.

갑자기 머리가 아파집니다.


우선 GM툴이 만들어질때까지, DB쿼리를 만들어 테스트를 지원합니다.


자...다른 일정을 몇개 양보받고, 시간을 쪼개고 쪼개서 GM툴을 만들어 제공합니다.


이전보다 원활한 테스트가 진행되는군요.

자 이제 출시 준비를 하려는데… 통계툴을 요청받습니다.


….-_- 더 시간을 확보할 방법도 없는데…

최소한의 기능만 볼 수 있게 끼워 넣습니다…

남기고 있는 로그가 추출하기 적절한 로그가 아니라, 로그 기록 작업을 하느라 더 시간 소모가 컸군요.



어라? 당연히 필요한 결제 기능이 없었군요?

지원 해야 될 스토어가 세종류네요…

스토어별로 처리 방식이 달라, 세번 다 따로 구현해야 되겠군요...


자 어떻게든 선택과 집중을 통해 몇몇 기능과 퀄리티를 양보하며, 필요한 백엔드 작업을  그럭저럭 마친 것 같습니다.


게임을 출시합니다.


가아아아암동~ 몇달간의 노력이 드디어 빛을 발할 때 입니다.

유저가 몰립니다. 우오오오오~~


서버를 증설합니다!

이제 서버가 50대로 구성됐습니다.

이제 점검을 할 때마다 50대에 배포 해야 되네요…

한대당 2분 잡아도 패치만 100분이군요.

다행히 우린 서버 프로그래머가 2명이니 50분 정도면 될까요?


부족한 운영툴의 기능으로, 서버 데이터 패치로 이벤트를 진행합니다.


밤이 되었습니다.

유저는 여전히 많네요. 불안불안합니다.

새벽 3시가 됐음에도 유저는 별로 줄어들지 않네요.


혹시 몰라 서버 50대를 순회하며, 오류 로그를 모니터링합니다.


헐…! 사고가 났네요. 복구 및 보상을 해줘야겠습니다.


… 점검시점에서 모든 유저에게 보상을 주자니 너무 많네요.

로그인시 아이템을 지급하는 보상 시스템을 구현합니다…


…하… 복구를 하려했더니 백업된 데이터가 부족하네요. 백업/복구 시스템을 못갖춰놨었습니다.


이대로 롤백해야 되는걸까요…?

--------------------------------------------------------------------------------------------



자… 이쯤 되면 감이 오시나요?

서버라는 포지션 자체는 당연하게도 서비스를 위해 존재합니다.


비지니스 로직이 아닌 작업이 이렇게나 많이 필요하고, 당연히 많은 시간이 필요합니다.



물론 제가 나열한 작업 중에 여러 작업이 지원 부서가 있는 회사. 혹은 퍼블리셔에서 제공되는 기능들도 많습니다.


하지만 의외로 원하는 기능들 중 빠졌거나, 기능은 제공되지만 세부적인 기능이 달라 사용할 수 없는 일도 비일 비재합니다.


혹은 원하는 기능이 모두 있는 서비스는 비용이 비싸서 사용하기 부담스러운 경우도 생기지요.



가장 큰 문제는 이런 백엔드 작업들이 개발 초기 단계부터 일정 산정에 고려 대상이 아닐 때가 많다는 입니다.


개발 담당자가 직접 어필하지 않으면, 백엔드 작업은 프로젝트 전체 일정 산정에 고려되지 않을 공산이 큽니다.


개발 초기 서비스 일정을 산정하셔야 되는 분들이라면, 이 글을 읽으시고 하나라도 더 떠올리시어 백엔드 작업 일정과 작업 계획도 수립하시길 바라며 마치겠습니다.



-----------------------------------------------------

컨텐츠 제외 필요 작업 요약

-----------------------------------------------------

GM툴

통계툴

로그 기록 작업

결제 기능

배포

이벤트

모니터링

보상 시스템

백업/복구 시스템

Posted by 엘키 엘키

댓글을 달아 주세요

Thread design에 대한 이해는, 기본적으로 잠금 정책에 over head를 이해하고 있느냐에서 출발한다고 생각합니다.


잠금 기반 프로그래밍은, 자주 사용하는 코드가 잠기게 될수록 성능이 수직 하향합니다.

대기 하느라, 제대로 된 퍼포먼스를 낼 수 없다는 얘기죠.


그렇게 하지 않기 위해, 객체 간에 잠금에 신경쓰지 않게끔, 객체 간 접점을 줄여주어야 합니다.

 

좋은 Thread design의 목표는 어떻게 잡아야 할까요?

 

접점 최소화

손쉬운 비동기 처리

의도한 대로 순차 처리 (순서가 중요한 동작의 순서 보장)

 

디테일하게 나열하자면 얼마든지 많겠지만, 저는 위 세가지 목표가 보장된 기반 코드는, 컨텐츠 구현 시에 필요한 요구 사항을 다수 충족 시킬 수 있습니다.



이런 문제가 현세대 멀티스레드 프로그래밍의 최선이라고 여겨졌는지, 많은 솔루션이 이런 니즈를 충족시키는 데에 최적화되서 개발이 되었습니다.


node.js는 무거운 작업마다 비동기로 던지고, 그 결과 값을 바탕으로 진행할 다음 작업을 지정함으로써 잠금과 순서를 고민하지 않는 프로그래밍을 유도하고 있습니다.

만약 무거운 작업을 비동기로 처리하지 않는다면, 프로그래머의 실수라고 규정 짓는 가이드라인을 제시했습니다.



erlang도 마찬가지입니다.

기본적으로 메시지로만 통신을 유도하면서, 각 작업 간에 겹치는 상황을 제거함으로써, 잠금을 고민하지 않도록 했죠.



이렇게 할때의 언어에 구애 받지 않는 핵심은, 작업마다 독립적으로 동작할 수 있어야 한다는 점입니다.




로직을 작성하는 데에 있어서, 이 객체마다 잠금을 걸었다 풀어주는 과정은 잠재적 성능 저하 지점을 만드는 과정이라 볼 수 있습니다.


아무리 측정을 자주 하는 팀이라 할지라도, 기존에 (논리적으로도, 성능 적으로도) 잘 동작하던 코드가 병목이 될 수 있는지 여부는 의심을 덜하기 마련이기 때문이죠.


그런 잠재적 우려 지점을 변수가 추가될 때 마다 늘리는 방식은 결코 좋다고 보기 어렵다는 결론에 도달해, 현재의 모델이 최선이라고 느끼는 상황이죠.



애초에 작업들이 모두 작게 쪼개져 있고, 그간에 영향을 받지 않는다고 확신 할 수 있다면 당연하게도 대기 없는 비동기 처리가 가능해집니다.


로직을 작성하는 사람이 고민해야 될 대상중에 순서만이 남은 것이죠.


작업들을 비동기로 분리하고 난 뒤의 로직의 순서 조절은 상대적으로 쉬운 문제가 됩니다. 결합도를 고민하지 않아도 되는 상황이 되어버렸기 때문에, 순서 보장 기능을 라이브러리나 프레임워크 단에서 지원 (혹은 스크립팅으로 조절) 해주기 쉽고, 그렇지 않은 경우에 구현하는 문제도 순서 보장 작업끼리 같은 큐를 사용하게만 해줘도 되는 것이죠.



요약하자면 비동기 프로그래밍에서의 성능을 장점으로 삼는 다수의 언어와 프레임워크가 내린 합리적인 선의 비동기 프로그래밍은, 작업간 결합도를 줄인 후, 작업을 병렬로 수행해 성능 향상을 노리는 쪽으로 가고 있습니다.


제 생각도, 합리적인 선의 선택이라고 보여집니다. 극한의 성능도 중요하지만, 로직 작성의 난이도를 낮추는 것도 중요한 문제거든요. 실수할 여지를 줄이는 장점도 물론 옵션이겠고요.



지금까지 thread-design에서의 잠금 최소화 프로그래밍에 대해 알아보았습니다.


Posted by 엘키 엘키

댓글을 달아 주세요

http://weblog.rubyonrails.org/2016/6/30/Rails-5-0-final/


Rails 5.0이 정식 릴리즈 되었습니다.


드디어! 웹소켓을 지원합니다.

Action Cable이 바로 그것이죠.


기존 rails의 구조가 1 request-1 response를 기반으로 하는 만큼, 얼마나 웹소켓의 이벤트와 Rails ActionController 코드와 유연하게 연동이 되는지는 궁금합니다.


벌써 한글로 된 채팅 앱 구현 글이 올라왔네요!

http://blog.ask.co.de/2016/06/%EB%A0%88%EC%9D%BC%EC%A6%88-5%EC%9D%98-%EC%95%A1%EC%85%98-%EC%BC%80%EC%9D%B4%EB%B8%94%EC%9D%84-%ED%99%9C%EC%9A%A9%ED%95%9C-%EC%B1%84%ED%8C%85-%EC%95%B1-%EA%B5%AC%ED%98%84/


Api Mode는 back-end로 client-side javascript나 native-application과 JSON으로 통신이 가능하다고 하네요.


정확히 어느정도로 다른 어플리케이션과 유연하고, 성능상 잇점을 가져다줄 기능이 구현되었는지는 확인해봐야 알거 같네요.



빠른 개발 속도와, 상대적으로 낮은 학습비용에 비해 성능 문제와, 진입 자체는 쉽지만 많은 이해도를 요구하는 난제들도 함께 했던게 사실인 rails.


특히나 성능 문제로 인해 twitter는 rails를 포기하기도 해 많은 우려를 낳고 있었는데요, rails 5는 그런 우려를 불식시키고, 다시금 많은 장점으로 사랑받는 웹 프레임워크로 입지를 확고히할지는 더 두고 봐야할 문제라고 생각합니다.


자세한 Rails 5 차이점에 대한것은 제가 조금 더 사용해보고 알려드리겠습니다.


rails 5에 대한 간략한 사용법과 특징을 정리한 유투브 영상 한편 소개해드리며, 마무리할게요.




'Web > Ruby on Rails' 카테고리의 다른 글

Rails 5.0 Release  (0) 2016.07.02
vscode with rails  (0) 2016.04.14
rails aptana studio에서 디버깅 안될 때  (0) 2015.04.14
Rails를 이용한 웹 로그 서버 구축기 ver2  (0) 2014.12.16
Ruby on Rails 소개  (1) 2014.12.02
windows 환경에서의 mysql2 gem 문제  (0) 2014.11.12
Posted by 엘키 엘키

댓글을 달아 주세요

이전버튼 1 이전버튼

블로그 이미지
Software Engineer
엘키

공지사항

Yesterday31
Today29
Total1,605,483

달력

 « |  » 2016.7
          1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
31            

글 보관함