노스모크성능개선

FrontPage|FindPage|TitleIndex|RecentChanges| UserPreferences P RSS
느려진노스모크노스모크운영비문제를 해결하기 위하여 노스모크성능개선을 해야한다. 그 방법에 대하여 알아보자.


내부처리속도와 유지비

RAM이용 가능성

노스모크 데이터를 전부 dump하여 MoniWiki위에 구동해보았습니다. DB자체가 파일구조기 때문에 속도가 확연히 차이 나진 않은듯 합니다. 하지만 MoinMoin보다는 렌더링 속도에서 상당히 이득이 있는듯 합니다. 페이지는 거의 유지가 되더군요 --ziozzang

램 드라이브에 올리는 미친 짓을 감행한다면... 속도가 향상될지도 모르겠군요... -_-;;; --아무개

램드라이브도 꽤 괜찮은 아이디어 같습니다. 저장할 때 하드에 동시에 저장하고 읽는 것은 메모리로 한다면 꽤 괜찮을듯 합니다. 어차피 서버 호스팅이거나 코로케이션일텐데. 하지만 데이터가 변경되는대로 모두 사본으로 저장되는 구조는 용량상 버전 콘트롤링 시스템이 필요해 보입니다. 지금 상태로는 용량으로도 봤을 때 오래 견디기가 조금 껄끄러운듯 싶구요(메모리로 올리는것도 문제!). 가장 좋은 방법은 MySQL과 같은 DB를 사용 하는게 아닐까요? --ziozzang

노스모크가 차지하는 용량 자체는 매우 적습니다. (수십 메가바이트 정도) 페이지뷰가 매우 많아서 전송량이 높습니다. -- DaNew

데이터만 차지하는 용량은 23메가 정도 됩니다. (2003년 12월 27일 오후 11-12시 현황) 하지만 노스모크 데이터 자체가 버전 큰트롤시스템을 사용하는게 아닌 변경사항을 모두 저장하는 방식이기 때문에 조금 문제가 된다 라는 이야기 였구요. 데이터 뿐만아니라 DB파일이라던가, 유저 파일등도 메모리에 함께 올라가야 하니 그것보단 크겠지요. 이 부분에서는 RCS등의 버전 콘트롤링 시스템이 필요하지 않나 싶습니다. 메모리 드라이브를 만들어 마운트 하는건 루트 권한만있으면 꽤 괜찮을듯 합니다. 하지만 용량이 얼마나 늘어날지, 장담하긴 그렇군요. 하지만 관리라던가 유지 덕분에 램 드라이브를 쓰는것보다는 DB로 잠재적 이전이 필요하지 않나 생각 됩니다. --ziozzang

데이터 양이 작다면 램드라이브는 별 효과 없을겁니다. 이미 OS의 buffer cache에 모두 올라왔을테니깐요. --병권

램드라이브 사용의 더 효율적인 방안

최신버전의 text만 램드라이브에 올리고 '링크' 하면 오케이입니다! ^^ MySQL으로 올리면 검색속도는 2배 정도 빨라지더군요. editlog도 램 드라이브에 올린다면 어느 정도의 속도 향상이 있을지 사뭇 궁금해지네요. 용량은 '최신버전'만 올린다면 크게 문제될 것이 없겠지요? --아무개

데이타베이스의 활용

예상을 뒤엎고 텍스트 파일에서 뽑아오는 PHP 페이지가 MySQL에서 가져오는 PHP 페이지보다 약 16배가량 빨리 응답했습니다. PHP 페이지를 잘못 만들었는지 확인을 해봐야겠군요. ... index를 제대로 설정 안하고 한 것이 잘못이었군요. 다시 테스트하겠습니다. index를 지정하고도 2배가량 차이가 나네요. 페이지 접속을 할 때마다 다시 데이터베이스에 접속하니까 그런가 봅니다. 영구적인 접속으로 변경하고 다시 해보겠습니다. ... 이제서야 파일 기반보다 더 빨라졌습니다. ... 아니, 오류가 났었군요 -_-;. 보안문제(사실은 메모리 문제겠지요?)로 호스팅 회사에서 영구적인 접속을 막아놓았습니다. ... 접속과 동시에 내용을 읽도록 변경하니까 1.5배로 차이가 줄어들었습니다만, 여전히 텍스트 파일에서 뽑아오는게 빠르군요. ... --아무개

오버헤드 때문이겠지요. 하지만 대용량의 경우는 파일보단 DB가 유리할겁니다. 그리고 캐슁을 하기 시작한다면 더 빨라집니다. Zend Performance Suite같은 제품을 쓰면 PHP는 날라다니기 시작합니다. (물론 수백가는 비싼놈입니다.) 그외에도 Python보다는 속도 증가를 할 수 있는 여지가 꽤 됩니다. 참 요즘 경우는 Perl도 빠르게 돌릴수 있는 방법이 있더군요. PHP처럼 Perl을 메모리에 올리고 쓰는 방법이 나왔더랩니다. Python도 어느정도 그런 방법이 가능할듯도 합니다만. 아직은 잘모르겠습니다. --ziozzang

아무래도 데이터베이스 호출의 오버헤드 때문인 것 같습니다. 영구적인 접속을 할 수 있다면 훨씬 나아질 것 같습니다. 그런데 더 큰 문제는 대용량의 파일을 잘 쓰지 않고, Zend Performance Suite를 쓸 정도로 돈이 넉넉치 않다는데 있습니다. 뒤에 말씀하신 방법은 mod_perl과 mod_python, FastCgi 등의 방법인 것 같습니다. --아무개

뭐 사실 아무말도 안하고 살짝(...) 쓴다면 뭐라 말할 수 있는 계제는 아니지요. 하지만 그건 아무래도 양심상의 문제니까. 아 퍼키님이 요즘에 Python 커미터로 들어가셨다니 부탁을 해보는게 어떨까요? 그것도 아니면 apache module로 하나 짜는것도 괜찮지 않을까 생각 해봅니다. --ziozzang

주제와는 벗어나고 ziozzang님이 말씀하시는 메모리에 얹혀 두는 것이 무엇을 의미하는지 모르겠지만 (php와 같은 방법이라니 fastcgi를 의미하는 것 같습니다. fastcgi는 요즘에 나온 방법은 아닙니다만 :-) 제대로 관리된 제대로 관리가 되었다면 fastcgi된 perl이 php보다 훨씬 빠릅니다. 데이터베이스는 내부적으로 파일을 쓰니깐 김창준님의 말씀 처럼 관계를 담는 구조가 아니라면 효과적이지는 못할거라고 생각합니다. 관계를 다루는 구조라면 미리 짜여진 좋은 알고리즘에 의해서 효과적이겠지요.--씨엔

위키 텍스트 자체는 일반 RDBMS에 담기에 효율적인 구조가 아닙니다. -- RDBMS는 말 그대로 "관계"들을 담기에 좋은 데이타베이스입니다. RDBMS를 쓰는 것이 현재의 파일 시스템을 쓰는 방식보다 월등한 퍼포먼스를 낼 것이라고 생각하지 않습니다. 간단히 속도를 높힐 수 있는 방법으로, Prevayler같은 인메모리 디비를 쓰는 것도 좋을 것입니다(파이썬에도 인메모리 디비가 있습니다). 램 드라이브를 사용하는 것보다는 자료의 안정성이 높습니다. 전문(full-text) 검색 속도 향상을 위해서는 Lucene 같은(파이썬에서는 Lupy) 전문 검색 엔진을 사용하는 것이 좋지 않을까 합니다(CJK를 위해 bigram 토크나이징을 지원합니다). 현재 MySQL에서 전문 인덱싱을 지원한다고는 하나 아직 원시적인 수준이고 한국어는 제대로 처리하지 못합니다. --김창준


기타 방안

see also http://www.orbtech.com/wiki/PyPerSyst python 인메모리 디비인가보군요. --아무개

see also http://www.altibase.com 보십시오. 우리나라에서 만들었고, 현업에 적용한 사이트도 많군요. 단, MS역시 YuKon에서 IMDB를 지원할 것으로 보여서 그게 어떻게 진행될지 관심을 가지고 있긴 합니다. 아! 네 핵심에 벗어났군요-_- 하지만, 넓고도 크게 보는 것이 필요할 것 같기에...--JrCho
제가 생각해본 해결책은 저처럼은 두세번 페이지 고치는 수고를 하지않도록 한번에 제대로 쓰고 다듬는 법에 대해 홍보하는 것이 최저비용/최대효과를 내리라고 생각합니다. -- JrCho

Wiki:PrevalenceLayer는 정말 괜찮은 아이디어군요. 이유없이 DB가 싫었는데... :D --PuzzletChung

위키 데이터가 DBMS에 담기 적당하지 않다는 것은 일부 인정 합니다. DB에 담기보다 단일 파일로 저장하는것이 낫겠지요. 하지만 지금 계속 제기되는 문제점에서 볼때 Wiki에서 가장 필요한건 FullTextIndexing이라 생각 합니다. 이것이 가능한 무료 DB가 있을까요? --ziozzang

모인모인이 요청을 받으면 그때 렌더링하는 구조인가요? (아니라면 아래의 내용은 저의 상상에 지나칠수 있겠습니다)

그런 구조라면 글을 쓰는 순간에 html파일을 같이 만들어서 그것을 보여주는 구조로 한다면 상당수의 부하를 줄일수 있을 거라고 생각합니다. 노스모크에는 글을 편집하는 인구보다는 읽는 인구가 훨씬 많을겁니다. 위키 태그로 저장된 파일이 아니라 html파일을 준비함으로서 전체적으로 사용되는 하드디스크의 양은 늘어날것입니다. 하지만 미리 가공된 정보로 인해서 하드와 cpu의 부하는 훨씬 줄어 들거라고 봅니다. 그리고 RecentChanges에 대해서도 그런 처방은 주요할꺼라고 생각합니다. RecentChanges는 매우 많이 참고 되는 페이지 일겁니다. 이 페이지는 읽히는 용도보다는 쓰이는 용도가 훨씬 많을 겁니다. 이 페이지의 html버전을 만드는 임무를 마지막으로 수정된 페이지에 부담시킨다면 노스모크에서 글을 편집하거나 쓰는 시간보다 읽는 시간이 훨씬 많기 때문에 상대적으로 부하가 훨씬 줄어들꺼라고 봅니다. --씨엔

RecentChanges 페이지는 개인별로 커스터마이즈 됩니다(see 북마크사용법). 따라서, OriginalWiki처럼 북마크 기능을 없애고 속도를 높히거나, 아니면 RecentChanges에 어떤 슬롯을 두고 개인에 따라 그 슬롯을 채우도록 하는 일종의 "캐쉬된 템플릿" 개념을 써야 합니다. 다른 페이지들에 대해서도 캐슁을 하는 것은 간단하게 성능을 올릴 수 있는 방법입니다만, 캐슁을 효율적으로 하는 것은 쉽지 않습니다. 사용자가 어떤 액션을 했을 때 어느 페이지의 캐쉬가 갱신되어야 할지 명확하지 않은 경우가 있습니다. 매크로를 사용한 페이지들이 그렇습니다. 그러나, "더러워졌다"는 표시의 플래그를 시스템 전체에 대해 적용하기만 해도 상당한 성능향상이 있을 것이라 봅니다. --김창준

ecmascript와 cookie등의 client측면에서 해답은 나오지 않을까요? 그 쪽에서 해결할수 있다면 글 쓰는 순간들을 제외하고는 부하가 적은 "고정된 페이지"로 운용할수 있지 않을까 하는 생각이 듭니다. --씨엔

가능할 수도 있겠지만 아키텍춰 상에 변경이 필요한 부분이 있어서 노동량이 많이 들지 않을까 생각합니다. 어떤 정보는 포기하거나 혹은 변형하거나 하면 노동량을 줄일 수도 있겠습니다. 어찌되건 서버 부담이 줄어도 클라이언트 쪽에서 느끼는 속도는 비슷할지도 모르겠습니다. --김창준

아주 저사양의 에디팅 서버와 리딩용 프록시 서버를 함께 운영하면 무슨 일이 일어날까요. ROM족에게는 실시간 업데이트를 다소 포기시키는 방향으로 ROM족용 서버와 RAM족용 서버를 서로 싱크시키는 것은 위키위키 정신에 어긋나는 것이 큰 문제일지 모르나 효율성은 압도적으로 좋아질 것으로 보입니다. 하지만 노스모크의 개발방향을 그쪽 방향으로 가져가는데는 모두들 마찬가지시겠지만 musiki 역시 반대합니다. :) --musiki

생각해보았는데 클라이언트측에서 해결을 하더라도 김창준님의 지적처럼 사용자가 느끼는 속도는 향상되지 않을지도 모르겠군요. RecentChanges가 가장 큰 부담이 되는 부분일텐데 마땅한 해결책은 어렵군요. 언제 시간이 된다면 python을 지원하는 서버에서 테스트해봐야겠습니다. 김창준님이 언급하신 슬롯은 어떤 형태인지 구체적으로 알고 싶습니다. --씨엔

우선 프로파일링부터 한 후에, 시간 많이 걸리는 부분 중에서, 우선적으로 처리할 수 있는 부분부터 고치는 것이 좋을 것 같습니다. 이미 그렇게 하고 있나요? --지원

만약 RecentChanges가 클라이언트의 요청때마다 새로 목록을 작성하는 방식이라면, RecentChanges를 고정된 html페이지로 만들고, 무언가 RecentChanges에 기록되는 액션이 일어날때 RecentChanges페이지를 수정하는 방식으로 하는게 가능할까요?
위에서 나와 있듯이, 접속자마다 북마크에 따라서 RecentChanges가 다릅니다. 그렇기 때문에 의미가 없습니다. (접속자마다 html을 만든다고 해도, 페이지가 수정될 때마다 천 개의 html이 수정되어야 하기 때문에 의미가 없습니다.)

OriginalWiki처럼 개인 북마크를 없앤다면 어떨까요? --아무개

다른 방법이 안 되면 마지막 방법으로 고려해봅시다. (설사 그렇게 되어도, 북마크의 편리성을 희생하는 것이 좋을지에는 회의적입니다만) -- DaNew


이 작업이 지지부진한 것이 제 책임이 큽니다. 프로파일링은 전에 해보려 했는데, 라이브러리 레퍼런스에 있는 예제 정도의 지식으로는 실제로 돌아가는 CGI를 어떻게 프로파일해야 하는 것인지 잘 알 수가 없었습니다. 제대로 찾아보지 못하기도 했는데 cgi에 대해서 ab말고 다른 측정 방법을 보질 못했습니다. 제대로 알아봐야할텐데 당장 손댈 여력이 없어서 미루어놓았는데, 제가 메여있는 일이 꽤나 지연되고 있는 형편이어서 여태까지 신경을 못 쓰고 있습니다. fastcgi, scgi 등에 대해서도 마찬가지 이유로 알아보지 못하고 있습니다.

(이 얘기도 어디에 있었던 것 같은데) 서버를 학교에 있는 컴퓨터로 옮기는 것은, 제 생각에는, 개인 홈페이지라면 괜찮겠지만 노스모크 정도의 사이트가 학교 허락 없이 그래도 될런지 모르겠습니다. 연구실이나 교수의 후원 없이는 전산소의 허락을 받기 어렵지 않을까 생각됩니다.
--희상

MoniWiki + ZendOptimizer + mod_gzip 의 조합은 어떨까요? 개인적으로 한번 테스트해보고 싶지만 노스모크의 데이터도 없고 그만한 페이지 로딩을 시뮬레이션 하기는 힘들군요. --JStrane

Zend의 캐쉬 기능을 사용해보면 어떨까요? 물론 이미 충분히 논의된 사항이겠지만... TitleIndex가 29초나 걸리네요. --JStrane


그런데 솔직히 왠만한 페이지는 캐슁처리를 하면 좀 나아지지 않을까요? TitleIndex가 29초나 걸릴 이유는 없을꺼 같네요.. chungdna

분석결과, TitleIndex를 모두 가져와서 순서로 분류하는 단계까지는 매우 빨랐습니다. 이것을 html로 변환하는 과정이 80%이상의 시간을 잡아먹더군요. 그래서 옵션으로 하나의 인덱스(A,B,가,나)만 렌더링하도록 처리했습니다. 현재 3초 미만의 시간이 걸리네요.

TitleIndex와 더불어 Fullsearch도 15초~20초정도 걸립니다. 이것의 속도를 개선하려면 지금처럼 fulltext search가 아니라 text를 잘게 쪼개서 미리 index하는 indexer를 쓰도록 하도록 해야합니다. 이 방법을 적용하니 Fullsearch가 노스모크에서 3초 미만이 걸리네요. 조만간 반영하도록 하겠습니다. --무신


노스모크의 히스토리는 어떤 식으로 저장되나요? 화일 하나에 누적되는 형식인가요? 누가 답좀 해 주시길~ 저도 알아서 찾아보겠습니다. -- 안형진 2005-09-28 13:44:30

현재 노스모크는 MoniWiki엔진을 쓰고 있고, 파일 하나에 변경분만 저장됩니다. 이걸 delta라고 합니다. RCS,CVS와 같은 버전관리 프로그램이 이 포맷을 사용합니다. 매우 효율적인 방식이라서, 예전 노스모크모인모인을 사용할 당시에는 파일하나의 크기 ~ 백업본 하나의 크기라서, 백업이 100개라면 100배의 용량이 되지만, RCS, CVS를 쓰게되면 100개의 백업본이 페이지 10개 미만의 용량 밖에 되지 않습니다. --무신

근데 예전 히스토리는 영원히 사라진 건가요? -- 안형진 2005-09-29 14:03:59

제가 보니 남아있는(살릴만한) 히스토리도 얼마 없었고, 그래서 살리지 않은 듯 합니다만, 모니위키에서는 원한다면 모인모인의 히스토리를 그대로 가져다가 쓸 수 있는 스크립트를 제공합니다. 예전 사이트(이사가기 전 사이트)를 참고하세요. 삼차노스모크이전/문제해결 --무신



"; if (isset($options[timer])) print $menu.$banner."
".$options[timer]->Write()."
"; else print $menu.$banner."
".$timer; ?> # # ?>