스토리 홈

인터뷰

피드

뉴스

조회수 844

미국 상표 등록을 무료로? 선착순 이벤트!

안녕하세요, 대한민국 사업자들의 해외 전자상거래 진출(아마존 판매)을 도와주는 컨설팅 회사이자 업무대행사 컨택틱의 이이삭 대표입니다.오늘 여러분들이 매우 좋아할만한 특별한 기회를 준비해봤는데요, 바로… 컨택틱에서 여러분들의미국 상표 등록을 초특가로 대행해드린다는 것입니다. 한국의 변리사를 통해서 상표 등록하면 government fees(특허청 비용)까지 포함하여 총 120~150만원 내외인데요, government fees 즉 미국 특허청에 직접 지불해야하는 신청비가 고작 $225(TEAS Plus 신청 유형)인 것을 따지면 거의 100만원이나 변리사에게 수고비로써 주는 게 다소 버거울 수가 있습니다. 그래서 컨택틱에서 어떻게 해야 여러분들의 고민을 해소해드릴 수 있을까 고민을 해봤는데요, 2017년 6월에 26일에 컨택틱에서 직접! 변리사를 통하지 않고! 미국 특허청에 상표 신청을 해봤습니다. 단돈 $225만 지불하고 말이죠. 그리고… 2018년 1월 16일, 6개월 전에 신청한 그 상표가 LIVE 승인 되었습니다! 아래 사진을 통해 확인하실 수 있습니다.이렇게 한국변리사 또는 해외변리사를 이용하지 않아도 100% 효력 있는 미국 상표를 낼 수 있다는 것을 컨택틱에서 몸소 보여드렸습니다. 이 포스트를 보고 계신 여러분들께 컨택틱은 2018년 기념으로 무!료!로! 여러분들의 미국 상표를 신청 해드리겠습니다. 많은 분들 신청할 테니 모든 분들을 받을 수는 없겠지만 최대한 많은 분들의 미국 상표 신청을 도와드리고 싶습니다. 선착순 3명에게만 무료로 미국 상표 등록을 도와드리겠습니다. 빨리 신청하세요!1,500,000원  => 250,000원무료라고 해놓고 왜 25만원이냐...위에도 설명했듯이, $225 government fees미국 특허청에 직접 납부하는 금액입니다 ^^*신청 조건:(1) 미국 마켓플레이스 (이베이/아마존/월마트/등) 어느 한 곳에 상품이 등록되고 팔리고 있어야 합니다.(2) 해당 브랜드의 소유주임을 증명해주셔야 합니다.(3) 제품의 로고가 찍힌 실제 상품 모습 + 포장 박스 및 포장 비닐의 모습을 찍어서 보내주셔야 합니다.(4) 홈페이지가 있어야합니다 (영문 홈페이지 권장)(5) 브랜드 로고가 있어야 합니다.
조회수 2150

[과거 스타트업 경험]주문 폭주로 인한 2주동안의 CS 느낀점

필자가 다니고 있는 회사 brich는 패션 O2O커머스에서 굉장히 빠른 성장을 하고 있는 스타트업이다.각 트렌드 거리에 있는 (가로수길,삼청동,한남동,홍대 등) 오프라인 샵들을 모바일로 모아서 보여주고 고객들의 쇼핑 경험을 최적화시키는 것에 집중하고 있다.거리를 플랫폼으로 만들어 그 안에 여러 오프라인 매장들/디자이너들/브랜드들을 분류하고 위치 기반으로 나의 위치에 가까이 있는 샵/상품들을 검색,큐레이션 받을 수 있으며 궁극적으로 거리를 브랜딩하여 소비자들의 네비게이션 역할을 해주고 있다. "거리를 좁히다."이것이 우리의 미션이다.최근 오픈마켓 (지마켓,11번가)에 최초 입점을 통해 주문 폭주가 있었다. 단순한 입점의 형태가 아니라 긴밀한 협업의 형태였기 때문에 많은 트래픽을 우리쪽에 모으고 다양한 샵들이 집중적으로 노출될 수 있었다.지마켓,11번가는 패션쪽 카테고리를 강화하면서 수익의 볼륨을 높일 것이다.(아마존도 패션 마진율이 굉장히 높아 이 카테고리가 주력이다.그래서 자체 브랜드까지 런칭한다.) (어쩌면 지마켓,11번가의 제휴 제안은 수익의 볼륨보다도 우리를 테스트 베드로하여 자체 브랜드 런칭,혹은 독자적으로 O2O 패션 진행하고자 하는 실험일 수도 있다.)우리 브리치 입장에서는 좋은 샵과 좋은 상품들을 가지고 있기 때문에 유통 채널 다각화와 트래픽을 많이 모으면 된다.오픈 마켓에 좋은 노출 구좌들을 우리가 확보하고 그 트래픽을 활용하여 매출로 전환하면 서로 윈윈일 수 있다.지금 인터파크 사내 벤처였던 지마켓도 옥션에 입점을 통해 카테고리 하나씩 키우면서 설현이 나오는 오픈 마켓이 됬다.우리는 스타일 윈도우와 직접적인 경쟁을 하기보다 좋은 트래픽을 가지고 있는 지마켓이나 11번가와 긴밀한 제휴를 통해 같이 O2O시장을 크게 만들어나가면 된다.보통 좋은 샵을 발굴해서 그들을 성공시키는 것에 초점이 맞추어져 있는 나의 role을 잠시 쉬어두고 CS팀을 도왔다.그리고 그 과정에서 내가 느꼈던 점들을 공유하고 다시 한번 중요한 점들을 상기시켜보려 한다. 감정은 언어로 표현되지 않으면 죽으니깐 말이다.1.배송은 커머스의 생명이다. 특히 모바일 플랫폼 시대는 더더욱 그렇다.클릭 한번으로 음식이 배달되고 택시가 오고 스타일리스트를 부를 수 있는 시대이기 때문이다. 즉 클릭 한번으로 즉각적인 회사의 서비스를 경험할 수 있는 시대이고 우리는 온디맨드 경제(on demand economics) 흐름속에 살고 있다. 쿠팡이 물류센터를 직접 구축하고 로켓 배송을 하고 유니클로는 편의점과 전략적 제휴를 통해 배송에 스피드를 높힌다.그러나 스타트업이 이것들을 해내기에는 자금도 부족이며 인력도 부족이다.그렇기 때문에 배송이 빠르게 가능한 것들을 위주로 상품들을 준비하고 재고에 대한 준비가 필수다.그리고 배송 사고가 났을 때 어떻게 이것을 대처할지, 거기에 대한 발생 시나리오는 무엇 무엇이 있고 각각에 어떤 대응들이 가능한지를 생각하고 즉각 대응이 들어갈 수 있어야 한다.그리고 지마켓/11번가의 제휴에서 우리가 판매자지만 실질적으로 판매자는 재고를 가지고 있는 샵들이며, 이 샵들에게 재고에 대한,배송에 대한 약속을 지키지 못할 때에는 어떻게 할 것인가에 대한 패널티도 사실 협의를 해놓는 것이 맞다고 생각한다.책임소재를 명확하게 하는 것이 중요하기 때문이다.2.배송이 늦는 것은 일단 고객들의 불평 요소가 된다. 그러나 실질적으로 그 불평의 이유를 좀 더 깊게 들여다보면 늦는 그 자체에 있지는 않다.즉, 배송이 늦을 만한 합당한 이유가 있었냐 없었냐가 가장 중요한 문제이고 (대표적인 예로 수입 상품이라, 상품 준비가 오래 걸린다든지) 미리 늦는 것에 대한 공지가 있었냐 없었냐가 더욱 본질적인 요소이다.오픈 마켓의 셀러들은 보통 가송장을 발행하고 물건을 출고안하는 경우가 있는데, 큰 딜의 경우가 일어날 때 이렇게 가송장으로 처리하면 나중에 CS에 엄청난 타격이 온다.(그리고 판매자들은 패널티를 먹는 확률이 상승한다.지마켓 - 슈퍼딜 / 11번가 - 쇼킹딜 같은 경우는 판매자들이 3일내에 (72시간) 출고 원칙을 하는 것으로 한다.그리고 30개를 수량으로 판다면 30개가 필요한게 아니라 40개 정도(?)는 확보해놓아야 한다. 교환/반품/배송지연에 대비해서 말이다.보통 가송장에 대한 CS 클레임으로는 "왜 송장번호는 찍혀있는데 조회가 안되냐, 왜 배송은 안하냐, 배송은 안해놓고 왜 송장찍었냐"등등이 있다. (심한 경우는 지금 사기치냐 ㅠㅠ)그렇기 때문에 가송장으로 급한 불을 끄고 나중에 처리한다는 방식보다는 미리 배송지연에 대한 알림을 공지할 수 있는 대책을 마련하고 고객님들에게 지연이 되고 있다는 이유를 차근차근 설득시켜나가는 것이 중요하다.3.CS는 궂은 일을 하는 부서가 절대 아니다.고객의 최전선에서 고객 감동을 줄 수 있는 최적의 포지션이다. 그렇기 때문에 커머스를 운영하는 회사가 좋은 샵들만 소싱하고 비즈니스를 전개하고 있다는 것이 전제라면 고객의 재구매율은 바로 CS팀에게 달린 것이다.(예전 패션관련된 중국 담당자에게 듣기로는 중국에는 MD팀이 따로 없고 대표-CS 두 축으로 나누어져서 CS가 곧 MD이며 MD가 곧 CS라고) 따라서 커머스에서는 CS는 단순히 응대/게시판 관리 같은 것이 아니고 마케팅의 최전선 부서이고 그로스 해커들이다.따라서 CS를 담당하는 사람들은 고객의 불만 사항들을(배송지연/반품,교환처리 등) 데이터로 축적해 나가야되고 고객들의 main pain point를 파악할 수 있어야 된다.그래서 매달 그래프 변화율을 보면서 그것들을 개선시켜나갈 수 있어야 하며 상시 고객 관련된 데이터를 전사적으로 공유할 수 있는 문화를 만들어 나가고 토론해야된다.CS를 굉장히 잘하는 회사로는 자포스가 있고 훌륭한 CS를 통해 기업가치를 상당히 높혔다고 생각한다.자포스에 대해(기업문화) 자세히 설명되어있는 책(딜리버링 해피니스) 을 사놓고 읽어보지는 못했는데 꼭 읽어봐야겠다.(CS뿐만 아니라 재고/배송 관련된 영감도 많이 얻을 수 있을거라고 생각한다.아마존이 인수한 것도 결국 자포스의 문화를 산 것이 지배적인 의견이라, 회사의 문화를 공부하는 것도 많은 도움이 될 것 같다.)4.끝으로, CS의 동기부여가 굉장히 중요하다. 만약 이 동기부여가 고객 만족에 있지 않고 그냥 하는 일이고, 그냥 회사가 처리해야되는 그런 일거리에 그친다면 고객한테 일거리를 미루기 마련이고, 제대로 처리하지 않는 일이 발생한다.내가 그 고객의 입장이면 어떤 일처리 방식이 고객에게 행복을 줄 수 있을까를 끊임없이 고민해야한다. 회사의 프로세스를 너무 강조해서는 안된다. 상황에 따라서 고객의 감동과 행복이 극대화될 수 있는 의사결정에 집중해야된다.그리고 중요한 CS건들은 전사적으로, CEO와 공유될 수 있어야 된다.아마존 같은 경우에도 [email protected] (정확한 이메일 주소가 이것인지는 모르겠다.) 으로 베조스가 cs건을 공유받아 직접 처리할 것에 대한 대응을 하기도, 자기 생각을 말해주기도 한다고 한다.마치며CS에 2주동안 투입되면서 들었던 얕은 생각일 수도 있지만, 이 2주 동안에 우리가 이 사업을 왜 해야되는가, 나는 이 일을 왜 해야되는가, 나는 일의 동기부여로 어떤 것을 선택하고 있는가 많은 생각들이 들었다.CS는 고객 만족을 위해, 고객의 행복을 극대화시킬 수 있는 아이디어를 고민하는 사람과 동시에 행동하는 사람이다. 그러나 비단 CS뿐만이 그런가? 모든 스타트업 조직의 구성원들이 그런 마음가짐과 동기부여로 일을 한다면 우리는 스타트업을 통해 더 나은 세상을 만들고 더 좋은 세상으로 변화시킬 수 있지 않을까.- 이 글은 과거 필자의 스타트업 경험담 입니다.#페오펫 #peopet #스타트업 #창업 #경험담 #인사이트 #경험공유
조회수 1833

[CJ CGV] 유연한 조직을 만들기 위한 역발상? 

지난 8월, 영화를 넘어 문화를 선도하기 위해 노력하는 CGV에서 믿을 수 없는 소식(?)이 들려왔다. ‘사원이 멘토, 경영진이 멘티’가 되는 ‘리버스 멘토링(Reverse Mentoring)’을 진행한다는 것. 잘못 본거라고 생각했다. 멘토와 멘티가 서로 바뀐 것이 아니냐고 묻고 싶을 정도였으니까.하지만 사원이라고 새로운 것을 가르쳐주는 멘토가 되지 말라는 법이 없고, 경영진이라고 배움의 자세를 갖춘 멘티가 되지 말라는 법도 없는 게 아닌가! 이 프로그램을 통해 서로의 역할을 바꿔 상호 교류하며 세대 간의 격차를 해소하고 유연한 조직을 만들 수 있다면 이것은 금.상.첨.화! ‘리버스 멘토링’의 기획자 CGV 인사담당 이현주 님과 멘토·멘티로 참여한 CGV 천안펜타포트 김빛나 님, CGV 전략지원담당 조성진 님의 이야기를 들어보니 성공적인 프로그램이었다는 생각이 들었다. 리버스 멘토링, CGV라서 가능했다?▲(왼쪽부터)리버스 멘토링 기획자 이현주 님, 멘토로 지원한 김빛나 님, 멘티로 참여한 조성진 님. ‘리버스 멘토링’은 선배가 후배를 지도하는 전통적인 멘토링과는 반대로, 선배가 후배에게서 새로운 지식과 트렌드를 배우는 비형식적인 학습 프로그램을 말한다. 전 세계 기업에서 실시하고 있는 리버스 멘토링. 이 좋은 걸 CGV가 하지 않으면 섭섭하지~ 올해 CGV가 리버스 멘토링을 시작한 발단은 무엇이었을까? 2030세대를 알아야 CJ CGV의 문화도, 고객도 잡을 수 있어요. - 이현주 님 이현주 님은 주요 고객층이자 미래를 이끌어갈 성장 동력인 2030세대를 이해함으로써 CJ CGV의 바람직한 소통 문화를 굳건히 하는 한편 사원급 구성원들과의 세대간 격차를 줄이기 위해 프로그램을 고심하다 '리버스 멘토링'을 기획하게 됐다고 말했다. 지금은 CJ CGV 대표이사이신 최병환 님께서 올해 초 "2030세대의 시각과 트렌드를 이해하고 그들이 가진 인사이트를 공유하는 기회의 장이 필요하다"고 했던 이야기도 '리버스 멘토링'을 발족하는 원동력이 되었단다. ▲리버스 멘토링의 원활한 진행을 위해 여기저기 뛰어다닌 이현주 님. 많은 기업이 시행하는 프로그램이지만 중요한 건 성공 여부다. 진행했다는 것에만 의의를 두는 곳이 많았다. 그만큼 프로그램의 안착이 쉽지 않다는 것. 그러나 CGV는 달랐다. 여타 기업과 달리 구성원들의 낮은 평균 연령과 새로운 것을 수용하는 것을 꺼리지 않는 경영진, 그리고 수평적 커뮤니케이션이 가능한 환경 등 정착될 수 있는 요건이 갖춰져 있었다. 일일이 경영진을 찾아가 프로그램 목적과 취지를 설명하고 공감을 얻어낸 인사 담당의 노력도 한몫했다.그 결과, 대표이사를 비롯한 15명의 경영진들이 적극적으로 참여했다. 40여 명의 사원들은 프로그램 참가 이유와 자신 있는 분야를 적은 신청서 제출해 참여 의지를 내보였다. 멘티로 참여한 전략지원담당 조성진 님은 현장에서 근무하는 멘토들의 젊은 생각을 배우고 싶어서, 멘토로 참여한 김빛나 님은 현장에서 쉽게 만날 수 없는 경영진과의 만남과 회사의 가치관, 사업 인사이트를 얻기 위해서 신청했다고 전했다. 나의 멘토, 나의 멘티는 어디에?▲리버스 멘토링 서약서에 서명한 최병환 대표와 멘토로 참여한 사원들. 리버스 멘토링의 효과를 높이기 위해 멘토들과 적극적으로 소통하며 사전 준비를 철저히 했다. 멘토들이 직접 작성한 리버스 멘토링 신청 이유와 자신 있는 분야에 대해 추가적인 인터뷰를 진행해 유사한 주제별로 ‘멘토 그룹핑’을 실시했다. 이후 나온 주요 주제를 취합해, 이를 경영진들에게 보여주며 선택하도록 했다. 단, 멘토의 이름을 철저히 가렸다.‘나의 멘토, 나의 멘티는 어디에?’라는 궁금증은 지난 8월 2일 CJ 인재원에서 열린 리버스 멘토링 ‘Start-Up’에서 풀렸다. 첫 만남이라 어색한 기류가 흐른 것도 잠시, 뒷자리에 앉아 있는 경영진들을 대상으로 ‘신조어 테스트 및 아이돌 맞추기 게임’이 이뤄졌다. ‘핵인싸’ ‘JMT’ 등의 문제가 출제되고 답변을 못하는 경영진들이 속출하자 사원들은 놀란 표정을 지었다고. 누군가에게는 당혹스러운 시간이었겠지만, 젊은 세대의 트렌드를 알아야 한다는 필요성을 오롯이 느끼는 과정이었다. 답변을 못한 경영진들에겐 신조어 스터디에 대한 숙제가 주어졌다.그리고 대망의 15개 조 멘토-멘티 매칭 결과가 공개됐다. 어색한 기류가 흘렀지만 이어진 ‘미니 드론 날리기’ 프로그램을 함께하며 친밀감을 높였다. 원활한 스킨십을 위해 시합도 펼쳐졌는데, 팀을 위해 이겨 보겠다며 이쪽저쪽에서 연습하는 모습도 연출됐다. 이후 준비한 프로그램을 취소할 정도로 불꽃 튀는 대결이 이뤄졌다는 후문. 각자 멘토, 멘티 역할에 충실히 임하겠다는 서약서를 쓰며 4개월 간 최선을 다해 프로그램에 임할 것을 다짐했다. 멘티는 새로운 트렌드를, 멘토는 회사의 경영 방향을!▲한 번 팀은 영원한 팀! 우리는 ‘Back to the 20th’입니다. 인터뷰를 위해 나란히 자리에 앉은 조성진 님과 김빛나 님. 한 번 팀은 영원한 팀이라는 것을 내보이듯 최근 여행 다녀온 이야기로 꽃을 피웠다. 수많은 사람 중 한 팀을 이룬 조성진 님, 김빛나 님 그리고 두 명의 멘토들. 이들의 팀명은 ‘Back to the 20th’였다. 고심 끝에 지은 팀명에는 남다른 의미가 있다. 두 가지 의미인데요. ‘20대처럼 밝고 건강하고 신선하게 돌아가자’라는 것과, CGV 20주년을 맞이한 해로서 ‘초심으로 돌아가자’라는 뜻을 갖고 있어요. - 김빛나 님  ▲첫 번째 멘토링 핫플레이스 '보안여관'에 간 ‘Back to the 20th’. 팀명을 지은 후 이들이 한 일은 카톡 단체방 개설과 4개월간 해야 할 활동 계획서 작성이었다. 각 달의 주제와 함께 문화 공간과 체험 프로그램을 선정해야 했다. 트렌디함을 잘 알고 받아들일 자세가 된 멘티였다고 해도 멘토 입장에서는 트렌디한 장소와 체험 등에 대한 고민을 할 수밖에 없을 터. 많은 대화와 고심 끝에 첫 달 주제인 '트렌드 및 핫플레이스'에 맞춰 문화재생공간인 ‘보안여관’을 찾아갔다. 과거와 현재가 공존하는 이곳을 즐기며, 왜 많은 이들이 찾는지에 대한 이야기를 나눴다. ▲‘뮤직라이브러리’와 ‘아트 공방’ 체험을 함께하며 트렌드 소개 및 배우기에 올인! 두 번째 달엔 공통 관심사가 ‘음악’이라는 것을 감안해 ‘현대카드 뮤직라이브러리’에 가서 LP로 음악을 원 없이 들었다. 생전 처음 LP로 음악을 들은 김빛나 님은 새로움을 느꼈고, 과거 이를 많이 들었던 조성진 님은 향수에 젖었다. 이날 그는 과거 좋아했던 서태지의 음반을 계속 들었다고. 세 번째 달엔 ‘소비와 문화 및 여가생활’이란 주제에 걸맞게 '우연수집' 아트 공방 체험을 했다. 아크릴 판에 별을 새겨서 무드등을 만드는 작업이었다. 조성진 님은 직접 만든 무드등을 아내 생일 선물로 줘서 점수를 좀 땄다며, 멘토들 덕분이라고 공을 돌렸다.  2030세대에겐 극장 외에도 즐길거리가 많다는 걸 눈으로 확인한 기회였어요. 이번 프로그램을 통해 새로운 트렌드를 열린 마음으로 받아들이는 계기를 얻어 직장 생활에 새로운 전환점이 될 것 같습니다. - 조성진 님  모두의 노력으로 일궈낸 역발상의 기적, 내년에도 쭈~욱15개팀 모두 원래의 계획대로 리버스 멘토링 프로그램을 잘 해나가기를 바랐지만, 처음 진행한 프로그램인 만큼 경영진과 사원 간의 보이지 않는 벽이 존재했다. 이를 위해 인사 담당이 준비한 건 ‘멘.친.소(멘토의 친구를 소개합니다)’였다. 월별 활동 중 멘토의 선후배를 초대하는 프로그램으로, 멘토와 멘티의 가교 역할을 하면서 화기애애한 분위기를 조성하는 데 일등공신이었다. 프로그램 진행 중에는 멘토와 멘티에게 따로 설문을 진행해 서로가 느끼는 힘듦과 바람을 간접적으로 전달하고 틈틈이 인터뷰를 통해 서로 원활히 교류하고 이해할 수 있도록 도왔다. ▲기회만 된다면 내년에도 리버스 멘토링을 꼭 하고 싶어요! 멘토-멘티들의 적극적인 참여 속에 이뤄진 이번 프로그램을 마무리하는 지점에서 이현주 님은 나름 성공적이었다고 자평했다. 아쉬운 게 하나 있다면 더 많은 멘토들이 참여하지 못했던 것. 특히 멘토들에게는 경영진과의 소통 기회를 더 많이 누리게끔 하고 싶은 것이 그의 생각이었다. 2회 때는 올해 참여자들의 활동을 발판 삼아 다양한 방면으로 홍보에 박차를 가하고 형식에 얽매이지 않는 새로운 도전을 지속할 예정이다.리버스 멘토링을 직접 경험한 멘토인 김빛나 님도 많은 것을 느꼈을 터. 멘티에게 알려준 것보다 회사의 비전을 구체적으로 알게 되었던 것, 직장 선배이자 인생 선배로서 좋은 이야기를 많이 들은 것, 이를 통해 삶을 어떻게 보내야 할지에 대한 생산적인 고민을 많이 하게 되었다고 소회를 밝혔다. 이처럼 좋은 프로그램이 계속돼야 한다는 이들에게 각자의 바람을 들어 봤다. ▲리버스 멘토링. 내년에도 쭈~욱 이어지길 바랍니다. CGV에서는 리버스 멘토링 이외에도 다양한 멘토링 프로그램을 시행하고 있는데요. 이런 소통 문화가 잘 정착되어, 어느 회사에서도 따라잡을 수 없는 CJ CGV만의 소통 문화를 만들어 가면 좋겠습니다. 인사 담당에선 제도적인 환경만 조성하고, 멘토와 멘티들이 자발적으로 멘토링을 진행하는 문화로 발전되길 바라요. - 이현주 님 앞으로 많은 분들이 프로그램에 참여할 텐데요. 왜 참여하고, 어떤 걸 얻을 수 있는지 사전에 인식하고 적극적으로 활동하는 게 중요하다고 봐요. 멘토, 멘티 할 것 없이 즐기는 마음으로 좋은 활동하길 바랍니다. - 조성진 님 경영진에게 어떤 걸 알려줄 수 있을지 잘 몰라서 지원을 망설였던 분들이 많을 거예요. 그러나 걱정하지 말고 꼭 지원하셔서 유익한 시간을 보내세요. 리버스 멘토링, 앞으로도 계속 참여하고 싶습니다. - 김빛나 님 멘토링 프로그램의 궁극적인 목적은 멘토링 프로그램을 없애는 것이 아닐까 하는 생각이 들었다. 소통을 위한 장으로서 멘토링을 하는 것이니 소통 문화가 잘 이뤄지는 기업에서는 굳이 시행할 필요가 없는 것. 시작은 좋다. 중요한 건 이제부터! 멘토링 프로그램 없이도 원활한 소통과 유대감을 쌓아 발전해 나가는 CGV의 미래 모습, 그날을 기대해본다.[채널 CJ] #CJ #CJCGV #CGV #리버스멘토링 #멘토 #유연한조직 #기업문화 #조직문화 #구성원인터뷰 #역발상 #CGV공채 #CGV채용
조회수 1002

이메일도 반응형 디자인이 가능할까요?

이메일 뉴스레터를 제작하던 중 HTML 코드를 마주하게 된 경험이 있으신가요? 웹 기술과 HTML 코드에 익숙한 사람에게 조차도, 이메일의 HTML 코딩은 골치 아픈 주제입니다.웹 표준이 자리잡기 시작하면서 웹에서의 HTML 코딩은 많은 발전이 있었고, 효율적인 코딩과 다양한 기술 구현이 가능해졌습니다.하지만 이메일에서의 HTML 코딩은 상황이 많이 다릅니다.웹 표준이 지켜지기 전의 뒤죽박죽이던 HTML 코딩의 세계, 그게 바로 지금의 HTML 이메일입니다.HTML 이메일, 왜 필요할까요?텍스트로만 구성된 이메일(Plain-text Email)로도 충분히 메시지를 전달할 수 있습니다. 그럼에도 이메일 마케팅을 할 때 HTML 이메일을 사용해야 하는 이유가 몇 가지 있습니다.하이퍼링크. 다양한 요소에 하이퍼링크를 추가할 수 있습니다. 이미지나 버튼에 하이퍼링크를 추가하면 더 많은 사람을 랜딩페이지로 유도할 수 있습니다.디자인. HTML 잘 디자인된 HTML 이메일은 당신의 브랜드를 더 잘 표현합니다.위계. HTML 이메일에서는 콘텐츠의 위계를 만들 수 있습니다. 단락을 구분하거나 정렬을 다르게 하여 핵심적인 문구나 하이퍼링크를 쉽게 강조할 수 있습니다.추적. HTML 이메일은 오픈과 클릭을 추적할 수 있습니다. 오픈과 클릭은 마케팅 성과를 측정하고 전략을 개선하는데 참고할 수 있는 중요한 데이터입니다.이메일 코딩, 왜 다른가요?웹 디자이너와 퍼블리셔에게 이메일 코딩은 골치 아픈 작업입니다. 테이블 기반의 레이아웃 디자인, 인라인 스타일, 논리적이지 않은 구조의 마크업, 각종 꼼수로 대표되는 90년대로 돌아가는 것과도 같죠. 이유가 좀 많습니다.표준. 이메일에서 사용하는 HTML과 CSS는 웹 표준과는 거리가 멉니다. 이메일 클라이언트들 간에 표준도 없습니다.이메일 클라이언트들. 아웃룩, Gmail 같은 이메일 클라이언트들은 모두 HTML과 CSS를 다른 방식으로 해석하고 표시합니다. 가끔은 정말 그 정도가 심해서 어떤 클라이언트에서는 문제 없이 표시되는 이메일이 다른 클라이언트에서는 제대로 표시되지 않기도 합니다.꼼수. 정말 잘 디자인된 이메일들도 다양한 이메일 클라이언트에 대응하기 위해 각종 꼼수에 의존할 수 밖에 없습니다.자바스크립트. 자바스크립트는 웹에서 사용되는 가장 인기있는 언어 중 하나입니다. 하지만 이메일 코딩의 세계에 자바스크립트의 자리는 없습니다. 보안 문제로 이메일 클라이언트들이 자바스크립트를 차단하기 때문이죠. 당연한 처사입니다. 하지만 이 때문에 이메일에서 인터랙션은 포기해야 합니다.인라인 스타일(Inline styles). 웹에서는 본문의 구조(structure)를 정의하는 것과 스타일을 정의하는 것을 분리하여 더 쉽게 스타일을 관리할 수 있습니다. 하지만 대부분의 이메일 클라이언트들은 인라인 스타일(HTML 태그에 직접 스타일을 정의하는 방식)만 지원하기 때문에, 이메일에서는 어쩔 수 없이 인라인 스타일을 사용해야 합니다.다행히 많은 사람들이 시대에 뒤떨어진 이메일 코딩 환경에서 나름의 해법을 찾기 위해 노력하고 있습니다. 앞서 경험한 사람들이 그 결과물을 더 많은 사람들과 나누기 위해 공개하기도 합니다.Responsive Email Templates: 반응형으로 만든 다양한 유형의 이메일 템플릿을 무료로 다운로드 할 수 있습니다.The Ultimate Guide to CSS: 이메일 클라이언트별로 지원하거나 지원하지 않는 태그들이 일목요연하게 정리되어 있습니다.참고: Can Email Be Responsive?#슬로워크 #스티비 #마케팅 #마케터 #디자인 #디자이너 #CSS #인사이트 #꿀팁
조회수 1094

자바스크립트 기초 문법 정리 Part 3

함수와 이벤트에 대한 내용이 이렇게 간략할지 몰라 따로 파트를 나누어 포스팅을 진행하였는데 불필요한 나눔이 되었네요. 하지만 곧 더 간략하고 직관적으로 볼 수 있도록 기초 문법 총 정리 포스팅을 하도록 하겠습니다. 혹여 참고 문서로 본 포스팅을 보시는 분들은 곧 올라오는 총정리 포스팅을 참고하시면 좋을 것 같습니다.함수function 함수명() {    실행문;    return 데이터;}참조 변수 = function() {    실행문;}function 함수명() {(매개 변수1, 매개 변수2)    실행문;}   이벤트<button id="btn" onclikc="alert('event!')">버튼></button>이벤트 종류onmouseover - 마우스가 지정한 요소에 올라갔을 때 발생.onmouseout - 마우스가 지정한 요소에 벗어났을 때 발생.onmousemove - 마우스가 지정한 요소를 클릭했을 때 발생.ondvlclick - 마우스가 지정한 요소를 연속 두 번 클릭했을 때 발생.onkeypress - 지정한 요소에서 키보드가 눌렸을 때 발생.onkeydown - 지정한 요소에서 키보드를 눌렀을 때 발생.onkeyup - 지정한 요소에서 키보드를 눌렀다 떼었을 때 발생.onfocus - 지정한 요소에 포커스가 갔을 때 발생.onblur - 지정한 요소에 포커스가 다른 요소로 이동되어 잃었을 때 발생.onchange - 지정한 요소의 하위 요소를 모두 로딩했을 때 발생.onunload - 문서를 닫거나 다른 문서로 이동했을 때 발생.onsubmit - 폼 요소에 전송 버튼을 눌렀을 때 발생.onreset - 폼 요소에 취소 버튼을 눌렀을 때 발생.onresize - 지정된 요소의 크기가 변경되었을 때 발생.onerror - 문서 객체가 로드되는 동안 문제가 발생되었을 때 발생.참고문헌:Do it! 자바스크립트+제이쿼리 입문 - 정인용JavaScript 튜토리얼 문서 (http://www.w3schools.com/js/default.asp)티스토리 블로그와 동시에 포스팅을 진행하고 있습니다.http://madeitwantit.tistory.com#트레바리 #개발자 #안드로이드 #앱개발 #Node.js #백엔드 #인사이트 #경험공유
조회수 571

인사이트를 먹고사는 박쥐들의 생활양식 3종 세트

인사이트. 광고/마케팅/컨텐츠/디자인 이 네 개의 카테고리 아니 어떤 일을 하든 숙명처럼 따라붙을 수밖에 없는 단어 아닐까. 그래서인지, 우리 멤버들의 대화 속에서도 인사이트라는 단어를 자주 들을 수 있다. 매우 주기적으로 인사이트를 먹고사는 우리는 어디서 인사이트를 얻고 또 어떻게 서로 공유하는지 혹시나 궁금해할 누군가들을(?) 위해 박쥐들의 인사이트 생활양식 3종 세트를 소개해볼까 한다.하나, 인사이트 쉐어링주간회의가 있는 월요일의 첫 출근 날이었다. "자, 그럼 회의는 여기까지 하고 인사이트 쉐어링 해볼까요?"라는 말이 시작되자마자 띠링띠링 하는 소리가 들렸다. 무슨 소리인가 싶어 옆에 있던 멤버의 노트북을 슬며시 훔쳐보니 회사에서 사용하는 메신저에서 나는 거였다. Archive_Insight라는 채널에 파일, 이미지, 웹 주소 등이 공유되면서 나는 소리였던 것! 인사이트 쉐어링이란 한 주 동안 멤버들 개개인이 얻은 인사이트와 그 소스들을 공유하는 시간으로 좋은 디자인, 웹사이트, 브랜드 소식 등을 자유롭게 나누는 시간이다. 한 명이 물꼬를 트면 꼬리에 꼬리를 물고, '아, 그럼 저도!' 하며 다들 주섬주섬 인사이트를 꺼내 놓는다. 처음엔 일주일에 한 번인 주간회의 때만 반짝하고 마는, 비정기적 이벤트 개념으로 생각했다. 하지만 아니었다. 한 주의 시작인 주간회의가 물꼬를 트는 개념일 뿐, 이 채널은 매일같이 새 알람이 뜨며 (글을 쓰고 있는 지금도) 왕성하게 활동 중이다.실제 하루에도 몇 번씩 불이 켜지는 이 채널은 일종의 우리들의 보물창고 같은 곳이다. 가끔 일을 하다 리프레시가 필요할 때, 이 채널을 뒤적거리며 재미있는 컨텐츠를 보며 웃기도 하고 새로운 아이디어를 얻을 수 있는 소스들에 감탄하기도 한다.어느새 'Archive_Insight'는 가장 반기는 알림의 채널이 되었음을 슬쩍 고백해본다. 온라인 뿐만 아니라 오프라인으로도 인사이트 쉐어링은 자주 이루어진다. 여행을 다녀올 때, 출장을 다녀올 때도 좋은 것을 보고 들으면 꼭 멤버들 나눠줄 리플렛, 포스터 등을 보부상처럼 바리바리 싸들고 오는 정 많은 사람들.. 우리에게 인사이트 쉐어링은 일상이자, 일종의 동지애 같은 것이 아닐까?"인사이트...? 멤버들과 나누고 싶은 것!" - 이다솜 Branding Team Director둘, 도서 구매 지원(이라 쓰고 방라딘이라 읽는다)그렇다. 요즘 뜬다 하는 스타트업들이 그러하듯, 우리도 도서 구매 지원 복지가 있다! 이름하여 '방라딘'. 뭐하나 평범하게 넘어가는 법이 없는 우리는 이것마저도 네이밍을 했다는.. 절대 강요는 아니었..!!! AE 팀장 방정훈님의 관리 아래 운영되기 때문에 그의 이름에서 따온 네이밍이 만장일치로 당첨되었다. (디자이너 하나님의 의견이었다. 역시 핵인싸다워....) 방라딘의 이용 방법은 이러하다. 간단한 신청 이유와 함께 방라딘을 소환하기만 하면 끝. 그냥 진짜 끝! 그러면 총알처럼 접수해 일주일 안에 도서를 전해준다.단, 이 책을 완전히 내 것으로 만들기 위해서는 한 가지 미션을 완수해야 한다. 바로 '독서 노트' 작성하기. 이름처럼 심하게도 친절한 방라딘은 램프를 문지른 댓가로 이 노트를 요구한다. 양식만 보면 '그냥 내 돈 주고 살까' 싶은 생각이 잠시 들기도 하지만, 방라딘이 시키는 대로 정리하며 책을 읽다 보면 정말 그 책이 100% 내 것이 되는 신기한 경험을 할 수 있다. 작성한 독서노트는 멤버들 모두에게 공유되어 자연스럽게 인사이트의 역할을 한다. 이것이 바로 최소 비용에 최대 효율을 위한 방라딘(을 가장한 방정훈님)의 빅 피처였던 것이었다... "저에게 인사이트란, 좋은 작업을 하기 위해 끊임없이 스스로에게 자극을 주는 것이에요" - 이건용 Designer셋, 게더링 데이노마드 데이의 자매품이다. 한 달에 한 번 진행되던 노마드 데이를 격월로 줄이고, 그 빈 공간을 게더링 데이가 채우게 되었다. 노마드 데이는 토요일이지만, 게더링 데이는 무려 금요일이다. (야호!) 오후 3시경 각자 작업을 마무리하고, 미리 약속한 액티비티를 하러 떠난다. 볼링을 치는 팀도 있고, 방 탈출을 하러 간 팀도 있다. 머리 쓰고 몸 쓰기 귀찮다면, 산책 팀을 고르는 방법도 있다.그냥 놀러 가는 거냐고?맞다. 하지만 우리 멤버가 둘 이상 뭉치면 그곳에서는 인사이트가 뽑아지기 마련. 이번 게더링 데이에 산책 팀으로 참여한 나의 경험을 풀어보자면 이렇다. 신나게 사운즈 한남을 구경한 후 카페에 모여 이야기를 나누는데, 새로 산 가방에서 시작한 수다가 어느새 브랜딩에 대한 논의로 넘어가는 신기한 경험을... (가방<<<브랜딩) 어쩌면 게더링 데이는 일하느라 맘껏 떠들지 못한 인사이트들을 이참에 공유하라는 회사의 배려일지도. (아...아닌가?)"누군가와 대화를 할 때, 그 사람의 색다른 경험과 관점에서 인사이트를 얻어요." - 조윤성 AE
조회수 4738

피키캐스트 웹툰여신, 피키툰 담당자 ‘헤더’

안녕하세요, 매력 넘치는 옐로 구성원들을 소개하는 사내기자 Y의 옐플 인터뷰, 그 12번째 이야기! 이번 주인공은 바로 피키캐스트에서 피키툰을 담당하고 있는 헤더입니다. 매년 두 곳씩 여행을 다니며 얻은 영감을 바탕으로 계획하고 있는 독립출판 이야기부터, 열혈덕후가 추천해주는 웹툰을 지금 확인해보세요! Y: 안녕하세요! 옐블 독자들을 위해 간단한 소개 부탁 드려요. 헤더: 안녕하세요, 옐로모바일 가족 여러분! 피키캐스트 웹툰 서비스인 ‘피키툰’ 담당자 조혜림(a.k.a. 헤더)입니다. 반가워요 :) Y: 피키툰에서는 어떤 일을 하시나요? 헤더: 신규 작가 발굴부터 웹툰 리뷰 및 퀄리티 검수, 마케팅, 웹툰 서비스 개선 기획까지… A to Z를 관리하고 있어요. 특히 피키에는 대학을 갓 졸업한 신규 작가들이 굉장히 많은데요, 그런 분들을 발굴하는 과정이 정말 재미있어요:) 피키에서 인기가 많았던 '날라리'의 경우, PD가 대학교 졸업작품전에서 엄청 예쁜 그림체를 발견했다고 보여줬는데 보는 순간 반해버렸어요. 그 후 다양한 수정과정을 통해 피키에서 연재를 시작하게 됐습니다.피키툰 '날라리'Y: 그렇다면 그 중에서 가장 좋아하는 작품이 있나요? 헤더: ‘부기영화’라는 웹툰이요! 위트 있는 영화리뷰 웹툰인데, 아마 저처럼 영화를 좋아하는 사람들에겐 취향저격일거예요ㅋㅋ 그 외에도 학원 로맨스물 ‘러브 앤 위시’는 첫 회에 200만뷰를 찍을 정도로 인기가 많았던 작품이고요!  Y: 웽이 나오는 웹툰도 있던데요?헤더: 네! 웽은 옐로모바일 패밀리사인 디메이저 캐릭터인데요, ‘바보요정 웽’이라는 웹툰도 현재 연재되고 있어요. 요즘엔 핔플사이에서 웽은 피키캐스트 최고의 악역이라고 부르고 있어요. Y: 악역이라니! 왜죠?헤더: 실상 생활에서 흔히 볼 수 있는, 넘나 현실적인 악동이라 그런 것 같아요ㅋㅋㅋ Y: 피키와는 어떻게 인연이 닿게 되었나요?헤더: 좀 미친 소리 같지만…. 전에 다니던 회사가 너무 일이 편하고 업무도 많지 않아 약간 지루함을 느끼고 있었어요. 그러다가 아는 분을 만나러 피키캐스트를 방문하게 되었는데, 그 분위기에 반했어요. 마침 당시에 피키캐스트 채용 중이길래 지원하게 됐습니다.Y: 왜 이렇게 낯이 익나 했더니 피키 콘텐츠에 출연하셨더라고요! 헤더: 네! 최근에 부기영화에 그림으로 등장했습니다ㅋㅋ 이토준지에 나오는 ‘토미에’로 등장했는데… 아시는 분들은 아시겠지만, 딱히 정상적인 캐릭터는 아니잖아요? 작가님들이 저를 피키 아이돌로 만들어 주겠다더니 토미에로 만들어버렸어요ㅠㅠ피키툰 '부기영화'에 등장한 헤더Y: ㅋㅋㅋㅋ토미에ㅋㅋㅋㅋ 그리고 뱀파이어 메이크업 콘텐츠도 제보 받았는데요. 헤더: 헉, 보셨나요? 부끄럽네요ㅋㅋㅋ 정해진 메이크업 미션을 타이트한 시간 안에 해야 하는 뷰티마블 라이브쇼였어요. 20초안에 아이라이너 그리기, 거울안보고 10초안에 쉐딩하기….만약 한쪽 눈에 20초를 다 쓰면 그대로 한쪽 눈만 라이너를 하고 있는 거죠. 굴욕적인데 너무 웃겼어요.Y: 처음부터 피키툰으로 지원하신 건가요? 헤더: 아뇨, 사실 처음에는 마케팅으로 입사했는데 갑자기 만화를 담당하게 됐어요. 만화 쪽 경험이 없었지만 덕후라는 이유로 이렇게 좋은 기회를 주셔서 덕분에 너무 즐거운 마음으로 회사를 다니고 있습니다:)  Y: 특별한 취미가 있으신가요? 헤더: 우선 여행 다니는 걸 정말 좋아합니다. 일년에 적어도 두 번은 여행을 가는 걸 목표로 하고 있어요. 올해에는 치앙마이와 뉴욕을 다녀왔죠. 여행을 다니면서 현지 문화에 녹아 들고, 다양한 사람들과 어울리다 보면 일상에서 받았던 스트레스도 해소되고 힐링이 되는 기분이에요. 또 여행 다니면서 현지의 독특한 분위기를 사진으로 찍어 남기는 것도 좋아하고요.뉴욕(좌) 치앙마이(우)Y: 여행다니면서 겪었던 재미있는 에피소드가 있나요? 헤더: 예전에 핀란드를 갔을 때, Flow Festival에 참가한적이 있습니다. 핀란드 최대 규모 뮤직페스티벌인데, 아시안들이 정말 없더라고요. 그래서 그런지 방송사에서 인터뷰를 요청한적이 있어요. 인터뷰가 실제로 방송에 나갔는지는 모르지만요ㅋㅋㅋ헤더: 또 인테리어 꾸미는 데에도 시간과 노력을 많이 들이는 편이예요! 예전에 ‘오늘의 집’이라는 인테리어 앱에도 저희 집 인테리어가 소개된 적도 있고요.  Y: 인테리어 꾸미기라니! 그냥 유지하는 것도 어마무시하게 힘든데..!Y: 피키툰 담당자에게 웹툰 추천을 안 들을 수가 없겠죠? 헤더: 최근 본 작품 중에서는 레진의 ‘뼈와 살’이라는 웹툰을 추천합니다. 약간 19금 요소가 들어있지만(부끄) 마치 김기덕감독의 영화를 한편 본 느낌이에요:) 또 올레웹툰의 ‘말하기엔 사소한’이라는 작품도 무척 좋아합니다. 고립과 결핍, 외로움을 치유해가는 20대 후반 여성의 이야기에 마음이 아련해져요. 만화책으로는 우라사와 나오키와 아다치 미츠루, 야자와 아이의 작품을 좋아하고요. 최근엔 고다 요시이에와 요시다 아카미 작가에 빠져있어요!Y: 피키캐스트 입사 이후 가장 기억나는 에피소드가 있나요? 헤더: 예전에 고등학교 견학 프로그램을 기획한 적이 있어요. 그때 담당 선생님께서 아이들에게 좋은 경험을 하게 해줘서 정말 고맙다고 몇 번을 말씀하시더라고요. 견학이 끝나고 일주일 후에 손편지와 함께 엄청난 양의 닭갈비를 보내주셔서 피키 멤버들과 함께 나눠먹었어요. 사실 회사를 다니면서 경험하기 힘든 일이잖아요. 너무 감동스러워서 아직까지 기억에 남아요.  Y: 피키캐스트와 함께 하면서 좋은 점은 무엇인가요? 헤더: 제가 좋아하는 웹툰 분야의 일을 맡겨주셔서 너무 재미있게 사심을 채우며 일을 하고 있습니다. 업무가 만화 쪽이다 보니 매일 만화를 봐도 아무도 신경 쓰지 않아요ㅋㅋㅋ 덕업일치를 실현하고 있어서 행복해요.  Y: 앞으로는 어떤 일을 해보고 싶으신가요? 헤더: 제 오랜 꿈이 개인 서점을 운영하는 거예요. 어렸을 때부터 보수동 헌책방골목을 자주 갔었고 여행을 가면 현지 서점이나 헌책방을 꼭 찾아갈 정도로 개인서점 특유의 분위기를 너무 좋아해요. 언젠가는 꼭 제 손길이 가득 담긴 책방을 오픈하고 싶어요.Y: 올해가 얼마 남지 않았는데요, 그 전에 이루고 싶은 게 있나요? 헤더: 올해는 아니지만 이번 겨울 안에 이루고자 하는 목표는 있습니다. 제 친구 중에 사진작가를 하는 친구가 있어요. 저는 글을 쓰는 걸 좋아하고요. 둘이서 같이 포토에세이를 독립출판을 해보려고 해요.  Y: 마지막으로 못다한 한마디 부탁 드립니다! 헤더: 앞으로 피키툰 업무가 많아질 계획이라, 인원을 조금 늘리고자 하고 있어요. 만화를 좋아하는 분들! 이 업무가 내 업무다! 하시는 분들 이력서 마구마구 넣어주세요:D 앞으로 피키캐스트와 피키툰 많이 사랑해주세요! 감사합니다:)<현재 연재중인 피키툰 리스트>1.     먼지소녀 - 티끌모아 태산이라더니...2.     송사리 레볼루션 - 현실적인 듯 현실적이지 않은 쌍둥이 남매의 <혁명> 적응기3.     네임펜으로 그린 그림 - 홍승우 작가의 감성 터치 피키툰4.     2차원 개그 - 2차원개그는 두 컷으로 말한다! 상식파괴 피키툰5.     바보요정 웽 - 내가 바보인건 나 때문이 아니었어!6.     안녕 도깨비 - 평화로운 도깨비 마을에 나타난 인간 소녀7.     무국 - 학교에서 칼 들고 설치는 무서운 10대들의 세계8.     러브 앤 위시 - 섬세한 감성터치! 피키툰 최초의 순정만화9.     사랑이 커다래 - 교회오빠보다 더 설레는 오빠를 쫓는 9살 귀요미10.   여고를 아느냐 - 환상 따위는 거부한다! 거짓 따위 없는 리얼 여고 라이프11.   남팬인데요? - 남자 아이돌에겐 오직 여자 팬만 있단 생각은 금물!12.   부기영화 - 영화 본 뒤엔 만화로 해석 보자! 피키툰 최초의 영화 해석툰. 13.   토끼는 숨죽여 울고 있었다 - 당신의 소름을 책임집니다.14.   고구마 소녀 - 7년째 썸만 타는 역대급 답답이 고구마 소녀15.   날라리 - 미치도록 피하고 싶은 날라리와 왕따의 트루 로맨스16.   소음 - 같은 반에 내 스토커가 있었다17.   언무드셀라 - 게임 같은 삶을 꿈꾸던 당신에게 색다른 모험의 기회가 펼쳐진다면?18.   용사입니다 미용사 - 개성만점 미용과 학생들의 머리털 빠지게 웃긴 학교생활19.   연애에 서툰 뱀파이어 - 모태솔로 경력 170년! 격이 다른 연애고자의 등장20.   드리밍 - 8년의 내 인생이 꿈이었다면? 사랑을 되찾기 위해 꿈속으로 들어간 여자 21.   뚱뚱해도 괜찮아 - 이란성 쌍둥이 자매의 반전 연애 드라마22.   알아집니다 - 낭만의 섬, 제주도에서 펼쳐지는 도시 여자 생존기 23.   세계 최고의 꽃미남이 되다 - 아름다움의 기준이 뒤바뀐 세상! 24.   여름소년 - 1988년 여름 우리네 귓가에 초록의 총성이 울려 퍼집니다. 25.   에스 - 1988년에 일어난 최악의 연쇄살인사건! 피키툰 신작 범죄스릴러26.   메르헨 위치스 - 남자로 환생한 마녀는 과연 무사히 기사님을 찾을 수 있을까?27.   영원의 빛 - 집착해줘. 피키툰 최초의 욕망멜로28.   러브루저 - 언제까지 썸만 탈꺼야? 이제 연애할 때도 됐잖아!29.   부산늑대 - 부산 캠퍼스에서 시작된 늑대인간과의 로맨스30.   야귀록 - 강동원 뺨치는 퇴마사의 등장! 애절한 환타지 로맨스31.   시선 - 어디선가 나를 지켜보는 낯선 시선. 피키툰 공포 단편선
조회수 1556

도도 파이터 제작기

안녕하세요. 도도 파이터의 개발과 시각 디자인을 각각 담당한 스포카 크리에이터 박준규, 박지선입니다.우선, 도도 파이터에 관심 가져주시고 참여해 주신 분들께 감사의 말씀을 드립니다. 도도 파이터는 저희의 당초 예상을 훨씬 뛰어넘는 71명의 제출로 마무리되었습니다. 많은 분의 참여 덕분에 이벤트를 무사히 마칠 수 있었다고 생각합니다.이 글에서는 도도 파이터의 기획 의도와 제작과정, 기술적인 디테일에 대해서 다루어 보려고 합니다.기획 의도저희는 파이콘 한국에 2015, 2016년에 이어 이번 2018년까지 총 세 차례 후원사로 참여하였습니다. 저희는 매번 코딩 컨테스트를 열고 있는데 2015년에는 코드 골프1, 2016년에 코드 난독화2이벤트를 개최했습니다. 저희는 지난 이벤트들을 통해 파이콘 참가자들에게 오락거리를 제공하면서 재능을 발굴할 수 있었습니다그동안 다른 후원사들도 여러 가지 훌륭한 코딩 컨테스트를 열었습니다. 저희들은 이에 고무되어 2018년 파이콘 한국 참가를 결정하면서 새로운 코딩 컨테스트 이벤트를 만들어 보기로 했습니다.저희는 이번 코딩 컨테스트의 목표를 아래 세 가지로 잡았습니다.바이럴 효과가 있을 것사람의 눈을 사로잡을 수 있어야 할 것접근성 있고 직관적인 규칙을 제공할 것위의 점들을 고려해 봤을 때 인공지능 대전 격투게임의 아이디어는 비교적 자연스럽게 도출되었다고 생각합니다.유저 대 유저가 직접 경쟁하는 방식은 코드 골프나 난독화처럼 주최 측이 취합해서 평가하는 방식보다 훨씬 버즈를 만들기 쉽습니다.대전 격투 게임이라는 틀은 30년 넘는 세월 동안 거의 그대로 유지되어 왔기 때문에 수많은 사람들에게 익숙합니다. 그리고 두 사람의 대결을 가장 직관적으로 표현할 수 있는 포맷입니다.게다가 저희는 귀여운 마스코트 캐릭터도 가지고 있습니다. 귀여운 마스코트 캐릭터들이 투닥투닥 싸우는 모습을 누가 그냥 지나칠 수 있을까요.익숙한 장르이기 때문에 게임의 규칙 역시 큰 틀을 잡는 데 어려움이 없습니다.이런저런 다른 후보들도 있었지만 이러한 이유로 격투 게임을 만들자는 합의에 다다랐습니다.게임 디자인하지만 격투 게임은 직관적으로 보이는 외양에 비해 파고들기 굉장히 복잡합니다. 현존하는 대전격투 게임들은 수많은 캐릭터가 등장하고 캐릭터별 성능 차이와 상성 관계가 존재하며 대응 전략도 전부 제각각이기 때문입니다. 저희는 이러한 요소를 전부 배제하기로 했습니다. 그런 것들이 대전격투 게임의 본질을 관통하는 특성은 아니기 때문입니다. 그것들을 전부 벗겨내면 남는 본질은 심리전입니다. 상대방의 플레이 전략을 파악한 뒤에 정보를 취합하여 액션을 취하는 것이 대전격투 게임의 알파이자 오메가입니다. 저희는 이 게임을 턴제로 설계했는데, 보통 실시간으로 이루어지는 대전격투 게임을 턴제로 설계해도 말이 되는 이유가 여기에 있다고 생각합니다. 턴제로 만들어도 대전격투 게임의 본질이 심리전이라는 대전제가 깨지지 않기 때문입니다. 저희는 인공지능 대전으로 심리전의 특징을 살릴 수 있을 거라 보았습니다.여러 가지 시스템을 고려했으나 게임 디자인은 최소화된 형태로 수렴했습니다.플레이어는 뒤 또는 앞으로 한 칸씩 움직일 수 있다.공격 방식은 펀치와 킥이 있는데, 펀치는 숙여서 피할 수 있고 킥은 점프해서 피할 수 있다.심리전이 성립하기 위해서는 최소한의 상성 관계가 만족되어야 합니다.상대방의 공격을 무조건 맞는 대신 받는 데미지를 절반으로 줄이는 방어 액션이 있다.때로는 리스크를 지지 않는 안전한 선택지도 제공하면 좋을 것입니다.그 외에 게임 디자인 과정에서 여러 가지 시행착오가 있었습니다.처음에는 캐릭터를 움직인다는 개념이 없었습니다. 두 캐릭터들이 같은 위치에 서서 싸운다기보다는 가위바위보를 하는 모양에 가까웠습니다. 그래서 캐릭터 이동 액션을 추가했습니다.그런데 스테이지 크기에 제한이 없었습니다. 플레이어가 무한히 뒤로 갈 수 있었는데 한 대 때린 뒤에 끝날 때까지 뒤로 도망가는 파훼가 불가능한 전략을 쓸 수 있었습니다. 스테이지 크기에 제한을 두는 방식으로 해결했습니다.원거리 공격, 대쉬, 필살기 등등 여러 가지 세부적인 시스템을 고려했으나 시스템이 지나치게 복잡해질 것 같았고 무엇보다 제때 밸런스를 조정할 자신이 없어서 포기했습니다.시스템을 이렇게 만들어 보니 상대가 근접하면 가만히 서서 공격만 하는 에이전트가 승리할 확률이 가장 높았습니다. 이를 방지하기 위해 최근 다섯 턴 간 취한 액션이 한 종류라면 데미지가 1/3, 두 종류라면 2/3만 들어가도록 페널티를 주었습니다.이 조치만으로는 방어/회피 없이 공격만 해도 이기는 문제를 해결하지는 못합니다. 따라서 방어/회피에 성공할수록 다음 번의 공격력이 강해지는 시스템을 추가하여 적극적으로 방어/회피를 하도록 유도하였습니다.저희는 데미지 계산 공식을 공개하는 것을 주저했는데, 구체적인 공식을 공개하면 제출물의 성향이 한쪽으로 쏠릴 것을 염려했기 때문입니다. 저희는 최대한 창의적인 솔루션이 많이 나오길 바랐습니다. 하지만 지금 돌이켜보면 구체적인 수치를 공개한다고 크게 바뀔 것이 있었나 싶기도 합니다.시각 디자인처음엔 격투 게임이라는 설정만 있었지만, 시각적으로 풍부하게 표현하기 위해 더 디테일한 기획이 필요했습니다. 그리하여 도도 파이터 만의 세계관을 만들어 풀어보기로 했습니다. 설정을 초반에 정하고 나니 캐릭터부터 모든 디자인이 술술 풀려갔습니다. 왜 게임을 만들 때 초반에 세계관과 시놉시스를 세세히 기획하는지 알겠더군요.원래 실제 도도새는 마다가스카르 동쪽에 있는 모리셔스 섬 해안가에 주로 서식한 것으로 추정된다고 합니다. 모리셔스 섬에 도도새가 모여 마을을 이루고 있는 모습을 상상했고, 그곳을 배경으로 도도 파이터가 펼쳐집니다.야자수, 뜨거운 햇빛, 맑은 바다. 그리고 자영업자가 많은 평화로운 도도 포인트 마을. 손님을 위해 더 좋은 매장을 운영하려면 체력은 필수. 각자의 방식으로 체력을 기르던 매장 사장님들이 최고의 체력왕을 고르기 위해 도도 파이터라는 대회를 개최하게 됩니다. 과연 체력왕 사장님은 누가 될까요?노을이 아름다운 모리셔스 섬에 숨겨진 도도 포인트 마을Lean하게 캐릭터 디자인하기짧은 시간 내 게임을 완성하기 위해서 그래픽 리소스 제작 비용을 줄여야 했습니다. (인력 서포트도 있었습니다3) 기존에 잘 정리되어 있는 디자인 리소스들은 이런 상황에서 특히나 빛을 발합니다. 파이터는 포포(도도새 캐릭터)로 한정하고 동작 디자인은 거의 통일하기로 했습니다. 또한, 게임 특성을 고려해 기존에 디자인되어 있던 반측면 조형만을 활용했습니다.다만 사용자간 구분이 필요하기에 각 캐릭터별 특색을 넣었습니다. 게임에 등장할 포포들은 매장 사장님이므로 격투게임에 등장하면 흥미로울 만한 업종에 계신(?) 포포만을 모셨습니다. 그리고 각 업종에 어울리는 패션 아이템과 구별되는 성격을 배합해서 총 3종의 캐릭터를 완성했습니다.도도 파이터 대회에 참가한 포포 사장님들스시 장인 포포: 철두철미한 성격으로 묵직하고 독특한 풍미의 시그니처 스시를 주 무기로 사용합니다.학원 원장 포포: 성실히 학생들을 지도하며 평소에 칠판 지우개로 팔근육을 단련해왔습니다.볼링장 사장 포포: 걱정이 많지만 볼링을 사랑하며 즐깁니다.도도 파이터에서 캐릭터는 총 9가지의 액션을 취할 수 있습니다. 기본 틀은 동일하지만 캐릭터별 특색을 넣는 것만으로도 단조로움을 없앨 수 있었습니다. 공격하는 무기는 잔인하기 보다는 귀엽고 웃긴 방향으로 해 산뜻한 분위기가 되도록 했습니다. 만약 스시 장인 포포가 칼을 들고 있었다면 게임 분위기가 살벌했을 것입니다.캐릭터들의 다양한 모습구현 상세서버서버는 아래의 소프트웨어 스택을 사용하여 구현하였습니다.파이썬 3.6Flask 웹 프레임워크PostgreSQL 데이터베이스SQLAlchemy 데이터베이스 라이브러리그 외에 설정 관리에는 settei, 데이터베이스 마이그레이션은 alembic 등 여러 오픈 소스 프로젝트를 사용하고 있습니다.이상은 스포카에서 사실상 표준으로 사용하고 있는 소프트웨어 스택이기 때문에 스포카 개발팀이 비교적 능숙하게 사용할 수 있습니다. 덕분에 3~4주 남짓한 짧은 기간 안에 완료할 수 있었습니다. 개발 당시의 급박한 상태가 그대로 드러나는 퀄리티긴 하지만, 소스 코드는 여기에서 받으실 수 있습니다. PR이나 버그 보고는 두손 두발 다 들고 환영합니다.프론트엔드게임의 프론트엔드는 Unity 엔진을 사용하여 개발하였습니다. Unity는 WebGL 타겟 빌드를 지원하는데, 이를 통해 웹 브라우저 위에서 실행가능한 WebAssembly 바이너리로 빌드할 수 있습니다.매칭 기록을 재생해주기만 하면 되는 간단한 부분이기 때문에 처음에는 런타임 바이너리 용량만 수 메가바이트에 달하는 거대한 게임 엔진을 쓰는 것이 내키지 않았습니다. HTML5 Canvas를 직접 써서 만들까 했지만, 생각보다 손이 많이 가고 제때 끝낼 자신이 없었습니다. 다행히 Unity로는 빠른 작업이 가능했고 절약한 시간만큼 애니메이션 효과와 시각적 완성도에 조금 더 시간을 투자할 수 있었습니다. 빌드 용량이 크긴 했지만, 결과적으로는 좋은 결정이었다고 생각합니다.배포 인프라도도 파이터는 Docker로 빌드되며, 스포카의 프로덕션 서비스에 사용되고 있는 AWS ECS 클러스터 위에 배포됩니다. 기존 인프라를 활용하여 추가적인 지출을 최소화할 수 있었습니다.지금에서야 말할 수 있는 사실이지만 도도 파이터는 파이콘 행사 중에도 미완성 상태였습니다. 여러분들이 도도 파이터에 참가하고 계신 와중에도 개발자는 부스 한구석에서 부리나케 작업을 하고 있었습니다. 급박한 과정에서 Docker와 ECS가 있었기에 빠른 배포가 가능했습니다.샌드박싱웹 앱 위에서 임의의 파이썬 코드를 실행을 허용하면 필연적으로 공격의 위협에 노출됩니다. 따라서 저희는 악의적인 코드가 실행되지 않도록 하는데 많은 노력을 했습니다.에이전트 스크립트는 메인 서버 프로세스와 격리되어 실행됩니다. 이때subprocess모듈을 사용합니다.스크립트는 바로 실행되지 않고 러너 안에서 실행됩니다.이때 러너에서는 스크립트가 다른 파일을 열지 못하도록__builtins__.open()함수를 지웁니다.러너 프로세스는 제한된 유저 권한으로 실행됩니다. 혹여나 다른 파일을 불러올 수 있는 가능성을 OS 레벨에서 차단합니다.보안상의 이유로 에이전트는 허용된 모듈만 불러올 수 있습니다. 러너에서는 스크립트의추상 구문 트리를 분석하여 허용되지 않은 모듈을 불러오는지를 검사합니다. 이때ast모듈을 사용합니다.러너가 참조하는 모듈을 에이전트 안에서 참조하지 못하도록sys.modules를 비웁니다.실수 또는 DoS로 스크립트가 무한 루프를 도는 상황을 방지하기 위하여 3초가 지나도 스크립트가 완료되지 않으면 프로세스를 강제로 종료하는 역할도 합니다.서버는 Docker 컨테이너 안에서 격리되어 실행됩니다. 만약 잘못된 코드로 인해서 서버가 죽는 상황이 생기면 ECS 클러스터가 자동으로 복원해 줍니다.가장 마지막으로, 모든 실행되는 코드는 기록을 남깁니다. 만에 하나 이 모든 보호 조치들을 우회한다고 하더라도 어떤 GitHub 아이디로 로그인해서 무슨 코드를 실행시켰는지 기록을 남겨서 사후에 추적할 수 있도록 하였습니다.느낀 점들무엇보다 대회 진행에 아쉬움이 진하게 남습니다. 참가자들을 여러 조로 나눈 것은 수시로 조를 배정하고 결승전 이전에 조별 우승자를 미리 선정하기 위함이었는데, 결과적으로 최종 제출 기한이 끝난 뒤에 조가 배정되고 결승 중계 현장에서 조별 우승자가 정해졌습니다. 이로 인해 결승 중계 진행이 많이 늘어졌던 것 같아서 아쉽습니다.참가자와의 소통을 위한 피드백 창구가 없었던 점 또한 아쉽습니다. 몇몇 참가자 분들께서는 직접 부스로 찾아오셔서 문의하시기도 했습니다. 생각하지 않은 것은 아니었는데 다른 시급한 작업이 우선이라 엄두를 내지 못했습니다.예상보다 참가자들이 많아서 결승전 중계 때는 시간이 많이 밀렸습니다. 플레이백 속도를 조절할 수 있는 기능을 넣었어야 했다는 아쉬움도 남네요.처음에 우려했던 밸런스가 붕괴하는 상황은 다행히 발견되지 않았습니다. 승리에 유리한 전략은 어느 정도 경향성이 있는 것으로 보이나 게임의 밸런스가 망가진 수준까진 아니라고 판단하고 있습니다.마치며여기까지가 장장 4주에 달하는 도도 파이터의 제작 후기였습니다. 후속 포스팅에서 이번 파이콘 한국 2018 세션에서 제출된 출품작들을 분석하고 어떤 참신한 코드가 있었는지를 알아보도록 하겠습니다. 읽어주셔서 감사합니다.특정 목적을 달성하는 프로그램을 가장 짧은 길이로 작성하여 겨루는 경쟁 게임입니다. ↩창의력을 동원하여 어떤 목적을 달성하는 코드를 가장 알아보기 어렵게 작성하는 경쟁 게임입니다. ↩디자인 서포트를 해주신 안정빈 디자이너에게도 감사를 표합니다. ↩#스포카 #기업문화 #조직문화 #개발자 #개발팀 #프로젝트 #후기 #일지
조회수 2047

아마존의 전략 VS 알리바바의 전략

아마존과 알리바바는 각각 미국과 중국에서 온라인유통의 절대강자로 성장했다.알리바바는 중국판 월마트라 불리는 ‘선아트’ 지분 36.16%를 29억 달러에 인수했으며, 선아트는 중국에 446개의 할인매장을 가지고 있다.아마존은 미국 최대 유기농 식품업체인 홀푸트를 인수했고 홀푸드는 미국, 캐나다, 영국에 460여개의 매장을 가지고 있다.두 회사는 앞다투어 인공지능, 빅데이터, IOT 등 테크놀로지를 이용해서 온오프의 경계를 허물고 새로운 유통방식을 선보이고 있다. 이 두 회사는 이런 면에서 매우 유사한 것처럼 보이지만 두 회사의 성장전략과 철학에는 근본적으로 다른 것들이 있다. 아마존이 중앙집권적 제국의 전략이라면 알리바바는 성벽을 낮춰 탈중앙화된 생태계를 구축하는 전략이다. 아마존의 ‘아웃사이드 인’ 전략: 고객(아웃사이더)의 눈으로 기업활동을 점검하며 경영전략을 짜는 것이다. 알리바바의 ‘인사이드 아웃’ 전략: 기업 자체적으로 기업의 역량과 강점을 진단해서 어떻게 매출과 점유율을 높일지 접근하는 방식이다. 자, 그러면 이 두 가지를 비교해보자. 아마존의 아웃사이드 인 전략아마존은 철저히 ‘아웃사이드 인’ 전략이다. 고객이 모든 판단의 기준이다. 아마존은 고객과 직접적으로 관련되지 않는다면 아무 데도 시간과 비용을 쓰지 않는다. Customer Obession이 있을 정도다. 그게 그의 Ego이다. (2017. 4. 18 쿼츠)아마존은 모든 서비스에서 누가 우리의 고객인가.그들이 필요로 하는 것은 무엇인가를 따진다.기술 개발이 선행이 아니라 고객의 니즈가 먼저이고 기술은 고객의 니즈에 맞춰 개발된다.아마존의 서비스 개발방식을 보자! 서비스 개발 전 보도자료 작성: -      어떤 식으로 언론에 발표할지를 상상하면 작성한다. -      보도 자료 작성이 어렵다면 소비자들에게 어필하기 어렵다고 판된돼 프로젝트가 폐기된다.FAQ 작성-      소비자가 새 서비스를 이용할 때 궁금해 할 점, 어려운 점, 문제점 등을 미리 고민하는 단계, FAQ를 읽었는데도 궁금증이 해소되지 않으면 프로젝트가 폐기된다. 이렇게 해서 등장한 아마존의 서비스들은-      비용대비 이익성이 떨어진다는 반대에도 강행한 아마존 프라임-      신용카드 정보만 입력하면 클릭 한 번으로 주문. 결제하는 원클릭 시스템-      온라인 주문한 뒤 오프라인 매장에서 수령하는 ‘드라이브 스루’-      접근성을 높인 웨사이트 유저 인터페이스  등등등 수도 없이 많다! 아웃사이드 인은 아마존이 소비자를 대하는 태도였지만, 동시에 아마존 제국을 설명하는 말이다. 아마존은 아마존 밖( outside)의 모든 유통을 제국 안(in)으로 집어넣고 있다. 재고 관리부터 물류까지 아마존은 모든 것을 직접 통제한다. 온오프를 가리지 않고 유통에 있어서만큼은 모든 것이 아마존 안으로 들어간다. (2017. 11. 22 포브스)아마존은 밑지고 최저가에 팔면서 고객을 장악한 뒤 경쟁자들이 나가떨어지면 순식간에 시장을 장악한다. 번 돈은 다시 고객 경험에 투자하면서 더 많은 고객을 아마존 제국으로 흡수한다. 동시에 더 많은 경쟁자가 나가떨어진다.아마존은 소비자에 집착하면서 깍고, 덜 벌로, 대신 그 돈을 투자해서 시장을 파괴한다. 겨우 살아남은 유통업체들은 자신의 제국에 복속시킨다. 알리바바의 인사이트 아웃 전략알리바바도 소비자를 강조한다. 그러나 우선순위는 오픈마켓에 입점한 중간 판매자들이다. 빠르게 변하는 시장에서 고객 니즈에 대응하는 것은 판매 일선에 맡기는 게 낫다는 것이다. 그래서 알리바바 유통채널에서는 중간판매자의 권한이 강조된다. 한 마디로 알리바바와 관계를 맺은 모든 기업이 아마존이 되게하겠다는 것이 마윈의 계획이다. 그래서 알리바바는 상품등록, 주문, 결제, 배송으로 이어지는 온라인 유통 시스템을 구축하는데 힘을 기울였다. 그것은 다음과 같다.1.    물류시스템 차이나오 네트워크’(Cainiao Network)데이터 기반의 스마트 물류 플랫폼: 주문이 접수되면 어떤 창고에서 어떤 택배회사를 거치면 가장 효율적으로 배송될지 15초 안에 계산한다. 이를 바탕으로 차이냐오와 계약된 3,000 여개 물류회사에 배송물량이 할당된다. 2.    결제 시스템 알리페이(AlliPay)전자상거래에 대한 불안감을 해소하기 위한 제 3자 지급결제 서비스이다. 고객이 결제하면 배송되는 동안 알리페이가 대금을 보관하고 있다가 물건 수령 후 대금이 판매자에게 지급된다.3.    소상공인 금융지원 ‘안트파이낸셜’마이크로 파이낸스 회사. 알리바바 플렛폼에 합류하고자 하는 온라인 사업자들에게 저금리 대출을 해주는 등 금융서비스를 담당한다.알리바바가 이런 식으로 중소기업자들이 알리바바 시스템에 뛰어들 수 있도록 생태환경을 마련한 이유를 마윈은 아래와 같이 같이 말하고 있다. 2016년 알리바바 총거래액은 5,500억 달러를 넘었다. 우리가 판매하는 것을 우리가 직접 배달하려면 500만 명의 직원이 필요하다. 이 500만 명을 어떻게 고용해야 할까? 유일한 방법은 서비스 기업, 물류회사 등에게 자율권을 부여해 이들이 효율적으로 이윤을 낼 수 있도록 돕는 것 뿐이다. 알리바바의 기술혁신으로, 1,000만에 달하는 중소기업파트너들에게 마이크로소프트, IBM 등과 경쟁할 수 있는 힘을 부여하려는 것이다. 인터넷 기술을 통하면 모든 기업이 아마존이 될 수 있다는 것이 우리의 철학이다.(마윈. 2017. 2. 14 CNBC 인터뷰) 결국 마윈의 전략은 알리바바가 제국이 되는 것이 아니라 중소기업파트너들을 아마존으로 만들어주겠다는 철학이다. 이 글은 TTimes를 참고로 작성되었습니다.              
조회수 6623

Elastalert로 로그 알람 구축하기

Elasticsearch로 로그를 수집하고 추세를 분석하기는 좋지만 실시간 알람을 받으려면 X-Pack Alerting 등을 이용해야 한다. 하지만 사용자 편의성 측면에서 개선할 점이 많다. 로깅 알람 전용이 아닌 다양한 용도로 커스터마이징해서 쓸 수 있게 설계한 탓일 수도 있다. 아무튼 대안을 살펴볼 필요가 있겠다 싶어서 Yelp가 공개한 Elastalert로 알람을(도) 적용해보았다.X-Pack Alerting과 비교했을 때 Yelp/elastalert의 장점은 명확하다. 무엇보다 시나리오별로 정해놓은 패턴에 따라 알람을 작성하면 일이 쉽게 끝난다. 여덟 가지 정도의 알람 타입이 있어서 상황에 맞는 템플릿을 가져다 쿼리만 살짝 고치면 된다.“Match where there are X events in Y time” (frequency type)“Match when the rate of events increases or decreases” (spike type)“Match when there are less than X events in Y time” (flatline type)“Match when a certain field matches a blacklist/whitelist” (blacklist and whitelist type)“Match on any event matching a given filter” (any type)“Match when a field has two different values within some time” (changetype)“Match when a never before seen term appears in a field” (new_term type)“Match when the number of unique values for a field is above or below a threshold (cardinality type)예를 들어 OutOfMemoryError라는 단어가 로그에 찍혔을 때 알람을 받고 싶다면 다음과 같이 Rule 파일을 준비한다.# Alert when the rate of events exceeds a threshold # (Required) # Rule name, must be unique name: OutOfMemoryError # (Required) # Type of alert. # the frequency rule type alerts when num_events events occur with timeframe time type: frequency # (Required) # Index to search, wildcard supported index: logstash-%Y.%m.%d* use_strftime_index: true # (Required, frequency specific) # Alert when this many documents matching the query occur within a timeframe num_events: 1 # (Required, frequency specific) # num_events must occur within this amount of time to trigger an alert timeframe: hours: 1 # (Required) # A list of Elasticsearch filters used for find events # These filters are joined with AND and nested in a filtered query # For more info: http://www.elasticsearch.org/guide/en/elasticsearch/reference/current/query-dsl.html filter: - query_string: query: "message: OutOfMemoryError OR log: OutOfMemoryError" # (Required) # The alert is use when a match is found alert: - "slack"기본 템플릿을 가져다가 filter에 들어갈 쿼리만 다시 작성하면 일이 끝난다. 파이썬으로 작성한 간단한 소프트웨어라 사용하기도 쉽고 Docker로 만들기도 쉽다. pip install elastalert 그 외에 경험한 특이사항만 정리하고 이 글을 끝내려 한다.Elasticsearch의 플러그인으로 작동하는 X-Pack과 달리 ElastAlert는 독립 실행 애플리케이션이다. Kubernetes 같은 환경에서는 독립 실행 애플리케이션이 더 관리하기 쉽다.알람을 추가/삭제할 때마다 도커 빌드를 하기 힘든 환경이라면 RESTful API를 지원하는 X-Pack이 편할 것이다. back-end / elastalert 같이 RESTful API를 지원하는 ElastAlert 환경이 있긴 하지만 도커 배포환경에서는 여러 모로 한계가 있다. 도커를 올렸다 내렸다 하더라도 설정이 날아가지 않게 하려면 고민이 많아진다. node 애플리케이션과 Python 애플리케이션 둘을 하나의 도커 이미지로 제공하다 보니 다른 문제도 많다. 이런 식의 구성을 구현해봤다면 무슨 이야기인지 알 것이다.ElastAlerts는 Index Aliases를 지원하지 않는다. 물론 오픈소스이니 소스코드를 고쳐서 Pull Request를 보내면 될 일이다.X-Pack Alerting과 달리 알람 메시지를 정형화했다. 알람의 메시지 포맷을 조금 고칠 수는 있지만 기본적으로는 주어진 그대로 써야 한다. 간단하게 쓰기에는 낫고 그렇지 않다면 소스코드까지 손을 대야 한다.ElastAlert는 중복 알람 처리 등의 정책을 지정할 수 있다. 알람을 하루에 수백통 넘게 받아보면 이 기능이 왜 중요한지 알게 된다.문서에서 언급하듯 Elasticsearch 5.x와 함께 쓰려면 다음과 같이 버전을 명시하는 편이 좋다. pip install elasticsearch>=5.0.0 && pip install elastalert==0.1.8테스트 환경은 elastalert-test-rule 명령어를 제공하는 ElastAlert쪽이 더 낫다. 검색 쿼리를 제대로 작성했는지 알람 설정은 맞는지 확인하기가 쉬웠다.더 읽기ElastAlert: Alerting At Scale With Elasticsearch, Part 1ElastAlert: Alerting At Scale With Elasticsearch, Part 2Originally published at Andromeda Rabbit.#데일리 #데일리호텔 #개발 #개발자 #개발팀 #일지 #후기 #도입후기 #Elastalert #인사이트
조회수 678

협업을 해치는 사일로 효과 극복하기

사일로 효과라는 말을 들어본 적 있으신가요? 아마 경영학과를 나왔거나 기업의 관리자라면 한 번쯤은 들어보셨을 겁니다. 사일로 효과는 한 조직 안에 개별 부서끼리 담을 쌓고, 각자의 이익만을 추구하는 현상을 말하는데요. 곡식의 사료를 저장하는 굴뚝 모양의 창고인 사일로(silo)에 빗대어 팀 이기주의, 부서 이기주의를 의미하는 경영 용어입니다.싸우지 마세요. 협업해야 합니다.사일로 효과는 조직이 제한적인 보상을 걸어, 서로 간의 경쟁을 과도하게 부추길 때 나타납니다. 또 부서별로 어떤 일을 하고 있는지 모르는 경우에도 사일로 효과가 나타나게 되죠.직원의 39%는 조직 내 팀원 간의 협업이 충분하지 않다고 생각했다.임직원의 86%는 직장 내 실패에 협업 부족이나 비효율적인 의사소통을 꼽았다.미국의 Clear Company의 설문조사에 의하면 참여자의 86%가 ‘팀의 문제와 실패는 협업이 부족해서 일어나는 일이다’라고 응답했는데요. 오늘은 협업을 해치는 사일로 효과를 극복할 방법에 대해 알아보려 합니다. 🤗1. 부서별 업무 공개하기첫 출근을 했을 때 부서별로 돌아가며 인사를 했던 기억이 납니다. 단순히 사람과 사람 간의 인사를 넘어 회사라는 조직 안에서 부서별 업무를 소개한 인사였죠. 부서별로 역할과 하는 업무를 세부적으로 알게 되니, 그 뒤부터는 협업하기가 편했습니다. A 업무는 A 부서에 요청해야겠다는 판단이 섰기 때문이죠. 부서별 업무를 투명하게 공개하면 타부서로부터 도움받기가 용이하고 때로 업무 분할도 가능합니다. 2. 조직의 공동 목표 제시하기일을 하다 보면 부서별 목표, KPI에 집중하게 되는데요. 이 목표가 서로 경쟁하는 형태가 되어서는 안 됩니다. 과거 IBM에서는 부서별 경쟁이 심해 1명의 고객에게 사업부별로 경쟁 입찰을 했다고 합니다. 고객의 입장에서는 같은 회사인데 왜…? 라는 물음을 갖게 되고, 회사 차원에서는 손해를 보는 장사였겠죠. 한 가지 더 예를 들어볼까요. 1986년, 미국의 우주 왕복선 챌린저호가 발사 후 73초 만에 폭파되는 사고가 있었는데요. 제작부에서는 날씨 영향을 받는 부품이 있어 발사 날짜를 늦춰야 한다고 했지만, 우주선 발사를 책임지는 부서에서는 발사 날짜를 맞춰야 한다고 주장을 했습니다. 결국 우주선은 발사되었고, 우주인 7명이 사망하는 비극이 발생했죠. 만약 이 두 팀의 최종 목표가 ‘성공적인 발사’로 같았더라면 어땠을까요. 부서 간의 협업이 되지 않으면 조직 간의 시너지 효과를 기대할 수 없습니다. 다른 부서를 통하면 쉽게 해결될 문제도 어렵게 해결하게 되고, 기업 혁신은 멀어지고 도태되게 되죠.3. 협업을 위한 업무툴 사용하기의사소통을 촉진하기 위해서는 개인의 노력만으로는 어렵습니다. 교육이나 지시로 부서 간의 협력을 유도하는 것은 한계점이 있죠. 그렇기 때문에 환경, 시스템적으로 제공되어야 합니다. 협업을 할 수 있는 협업툴이나, 사내 메신저 시스템이 필요하죠. 요즘은 재택근무를 많이 하므로 의사소통의 오류가 있을 수 있습니다. 가능하다면 화상회의가 가능한 업무툴을 찾아보는 것이 좋습니다.조직이 부서 이기주의, 사일로 효과에 빠지면 소통과 협업이 사라지게 됩니다. 개개인의 역량이 아무리 뛰어나다고 해도 결국 조직은 쇠락의 길로 빠지게 되죠. 평범한 사람들이 모여서 비범한 성과를 만들어내는 곳이라는 말처럼, 회사는 협업을 해야 하는 공간입니다. 자기를 지키기 위해 쌓았던 벽돌이, 오히려 자기를 갇히게 하지는 않았는지 확인해보세요. 😊협업툴 플로우 바로가기
조회수 1924

Docker, NodeJS, Nginx! 너로 정했다!

편집자 주아래와 같이 용어를 표기하기로 저자와 협의함Docker, NodeJS, NginxOverview안녕하세요. 칼 같은 들여쓰기에 희열을 느끼는 브랜디 개발자 강원우입니다! 서버를 운영해본 개발자라면 Fatal 에러, 아웃오브메모리 에러, 또는 전날 흡수한 알코올로 인해 손을 떨다가 한 번쯤 서버를 요단강 너머로 보내봤을 겁니다. 만약 테스트 서버였다면 잠시 마음을 가다듬으면 되지만, 현재 상용 서비스 중인 서버라면 얘기는 달라집니다.님아, 그 강을 건너지 마오!이런 간담이 서늘해지는 경험은 저 하나로 족합니다. 그래서 고군분투했던 지난 날을 되돌아보면서 빠르고 안정적이며, 죽어도 죽지 않는 좀비 같은 서버 구축 방법을 쓰려고 합니다.준비물서비스를 운영할 때 가장 중요하게 여겨야 하는 건 역시 안정성입니다. 이번 글에서는 오래 전부터 개발 세계의 뜨거운 감자였던 Docker와, 단일 스레드와 이벤트 루프로 태생적으로 심플하고 민첩한 NodeJS, 마지막으로 고성능을 목표로 개발된 Nginx를 활용하겠습니다.1. DockerDocker는 컨테이너 기반의 오픈소스 가상화 플랫폼입니다. 대표적으로 LXC(Linux Container)가 있습니다. 화물 컨테이너처럼 어떠한 일련의 기능을 완전히 격리된 소프트웨어 환경에서 작동하게 만드는 기술을 말합니다.OS 가상화와 별반 다를 게 없는 것 같지만 소프트웨어적으로 작동한다는 차이가 있습니다. 다시 말해, 현재 OS의 자원을 그대로 사용하기 때문에 하이퍼 바이저가 가상환경을 위해 가상의 커널을 만드는 오버헤드가 거의 없다는 것이죠.이미지와 속도도 차이를 보입니다. 완벽하게 구성한 세팅을 그대로 이미지화할 수 있고, 해당 이미지는 Docker 위에서 완벽히 동일하게 동작하는 걸 보장합니다. 해당 이미지로 컨테이너를 제작할 땐 1~2초면 새로운 컨테이너가 생겨날 정도로 엄청나게 빠른 속도도 자랑합니다. 1)또한 Docker는 자주 사용되는 다양한 이미지를 퍼블릭 레포지토리에 공유해 사용할 수 있기도 합니다. 양파도 아닌데 특징이 계속 나오죠? 다음 글에서 Docker의 특징을 더 자세히 다루겠습니다.Docker는 리눅스만 지원했었지만, 요즘은 Docker for Windows와 Docker for Mac으로 거의 모든 OS에서 사용할 수 있습니다. 2) Docker 설치 링크는 윈도우와 맥으로 나뉘어져 있습니다. 리눅스는 아래를 참고하세요.curl -fsSL https://get.docker.com/ | sudo sh 2. NodeJSNodeJS는 구글이 구글 크롬에 사용하려고 제작한 V8 오픈소스 자바스크립트 엔진을 기반으로 제작된 자바스크립트 런타임입니다. NodeJS에는 몇 가지 특징이 있습니다.단일 스레드입니다.비동기 방식입니다.이벤트 루프를 사용합니다NPM이라는 끝내주는 동반자가 있습니다.비유하자면 예전엔 낡은 곡괭이로 큰 돌을 캐내려고 수십 명의 인부가 달라 붙었는데, 지금은 육중한 포크래인으로 거대한 돌을 쑥! 뽑아버리는 것과 비슷합니다. 굉장히 효율적이죠. NodeJS는 단일 스레드의 장점을 극대화하려고 이벤트 루프를 통해 모든 처리를 비동기로 수행합니다. 서버 사이드의 묵직한 CPU들이 빠르게 일을 처리하고 이벤트 루프에 등록된 일을 감지해 다음 작업을 빠르게 수행하는 방식입니다.마지막으로 NPM(Node Package Manager)은 NodeJS에서 사용할 수 있는 다양한 모듈을 관리해주는 프로그램입니다. 도커와 상당히 유사합니다. NodeJS에서는 무언가 기능을 만들기 전에 NPM을 먼저 뒤져보라는 말이 있을 정도로 풍부한 모듈 생태계가 구성되어 있습니다. 이는 로깅이나 날짜 계산 등 생각보다 까다로운 것들을 가져다 사용할 수 있게 도와주기 때문에 개발이 빨라집니다. NodeJS 설치링크는 여기를 클릭하세요. 이 글의 예제에서는 NodeJS의 현재시점 LTS인 codename Carbon버젼을 사용합니다!8.x 버젼이 Active LTS 상태입니다.LTS은 Long Term Support의 약자로 가장 오랜기간 지원하는 버전입니다.우선 서비스 구성을 위해 간단한 NodeJS 어플리케이션을 작성해보겠습니다.첫째, packge.json를 작성합시다.{   "name": "nodejs_tutorial_server",   "version": "0.0.0",  "private": true,   "scripts": {     "start": "node nodejs_tutorial_server.js"   },   "description": "NodeJS Tutorial Server",   "author": {     "name": "WonwooKang"   },   "dependencies": {     "express": "^4.16.3",     "uuid": "^3.2.1"   } } nodejs_tutorial_server.js 파일을 메인으로 실행합니다. HTTP Request를 처리하려면 express를 사용해야 하며, 서버를 구분하려면 uuid모듈이 필요합니다.둘째, package.json의 의존 파일들을 설치합시다.npm install npm install 전npm install 후셋째, 간단한 웹 어플리케이션을 작성합시다.var express = require('express'); var app = express(); const port = 3000;  var server = app.listen(port, function () {     console.log("Express server has started on port : "+port);  });  app.get('/', function (req, res) {     res.send('Hello?');  }); 넷째, package.json의 script start 구문을 실행하여 서버를 로드합시다.npm start 3000번 포트로 서버가 시작되었습니다!접속해볼까요?잘 접속됩니다.그런데 수정할 때마다 서버를 매번 다시 띄우면 귀찮을 겁니다. 이럴 땐 nodemon 모듈을 사용합시다. nodemon은 Nodejs의 파일이 수정되는 걸 감지해 자동으로 리로드해주는 편리한 도구입니다.nodemon설치npm install nodemon -g package.json script 변경"scripts": {     "start": "nodemon nodejs_tutorial_server.js"   }, nodemon 실행확인을 위해 약갼의 수정//nodejs_tutorial_server.js 수정 app.get('/', function(req, res) {     res.send('Hello Nodemon');  }); nodemon을 통해 어플리케이션이 실행된 모습파일수정 후 저장했을 때 자동 감지한 모습서버 잘 떴습니다!성공적으로 단 하나의 GET 요청을 처리할 수 있는 심플한 NodeJS 기반 웹 어플리케이션을 완성했습니다. 이제 웹 어플리케이션을 Docker Container위에서 구동해봅시다!3. Docker로 NodeJS Express 서버 구동하기이제 Docker Container위에서 NodeJS서버를 구동할 건데요. 그러려면 우선 Dockerfile을 작성해야 합니다. 물론 Docker의 이미지를 당겨 받고, 컨테이너를 생성하고, 또 컨테이너를 실행해서 Attach하고, 필요한 파일들을 밀어넣는 등 귀찮은 방법도 있습니다. 하지만 개발자에게 이것은 힘든 작업이므로 Dockerfile을 적극 활용합시다. (Dockerfile의 D는 대문자여야 합니다! 꼭이요)Node 도커 이미지에 어플리케이션 파일을 추가해 실행하는 Dockerfile 작성하기FROM node:carbon MAINTAINER Wonwoo Kang [email protected] #app 폴더 만들기 - NodeJS 어플리케이션 폴더 RUN mkdir -p /app #winston 등을 사용할떄엔 log 폴더도 생성 #어플리케이션 폴더를 Workdir로 지정 - 서버가동용 WORKDIR /app #서버 파일 복사 ADD [어플리케이션파일 위치] [컨테이너내부의 어플리케이션 파일위치] #저는 Dockerfile과 서버파일이 같은위치에 있어서 ./입니다 ADD ./ /app #패키지파일들 받기 RUN npm install #배포버젼으로 설정 - 이 설정으로 환경을 나눌 수 있습니다. ENV NODE_ENV=production #서버실행 CMD node nodejs_tutorial_server.js Dockerfile 내용은 node:carbon에서 :carbon이 NodeJS의 이미지 버전 Tag 입니다.Dockerfile을 통해 docker image 빌드하기docker build –tag 레포지토리명: 태그 Dockerfile 경로docker build --tag node_server:0.0.1 [Dockerfile이 위치하는 경로] 호오... 게이지가 마구마구 차오르는군요?build가 완료된 화면입니다. Dockerfile의 내용 순서가 각 Step별로 진행된 것을 알 수 있습니다.빌드 결과 생성된 이미지 확인하기docker images 빌드 명령어에서 입력했던 버전 태그까지 잘 입력된 것을 알 수 있습니다.NodeJS Carbon 이미지를 기반으로 한 node_server 이미지를 제작했습니다. 사이즈는 둘이 합쳐 1Gb가 넘을 것 같지만 실제로는 변경된 부분만 저장됩니다. 그러므로 node_server 이미지의 크기는 6~10Mb 정도입니다.생성된 이미지로 컨테이너 만들기컨테이너 생성 명령어는 아래와 같습니다.docker create --name [서버명] -p [외부 포트:컨테이너 내부포트] [이미지명:버전태그] 주의할 점이 있습니다. 포트번호 바인딩 중 왼쪽은 우리가 접속할 실제 포트이고, 오른쪽은 컨테이너 내부의 NodeJS서버 할당 포트가 된다는 것입니다. 공유기의 포트포워딩 설정과 같습니다.docker create --name NODE_SERVER_0 -p 3000:3000 node_server:0.0.1 알 수 없는 코드가 생성되었습니다. 응?컨테이너 확인하기생성한 컨테이너를 확인해볼까요?docker ps 어.. 없잖아?옵션을 추가합니다.docker ps -a 나타났다!docker ps 명령어는 현재 실행 중(STATUS:Up)인 컨테이너의 목록을 보여줍니다. -a 옵션은 실행하지 않는 모든 컨테이너를 보여줍니다. 위의 이미지에서 node_server:0.0.1이미지로부터 NODE_SERVER_0 이라는 이름으로 2분 전에 생성되었다는 걸 알 수 있습니다. 3)컨테이너 실행하기docker start NODE_SERVER_0 다시 확인하기docker ps 19초 전에 Up상태가 되었다는 걸 알 수 있다.외부 3000번 포트 -> 내부 3000번 포트로 연결되었습니다. 서버도 실행되었고요! 이제 접속해볼까요?내용도 안 바꾸고 새로고침도 빨라서 뜬 건지 잘 모르겠군요. 내용을 수정해서 다시 확인하겠습니다.//nodejs_tutorial_server.js 수정 app.get('/', function (req, res) {     res.send('Hello I\'m In Docker Container Now!');  }); 파일 변경해서 다시 확인하기//버전 태그도 0.0.2로 업해주고 docker build --tag node_server:0.0.2 [Dockerfile위치] 잘 생성되었습니다.//이미지가 잘 생성되었는지 확인하고 docker images 0.0.2가 나타났습니다.//기존 컨테이너를 삭제합니다. -f 옵션은 실행중인 컨테이너도 강제로 삭제하겠다는 뜻입니다.  docker rm -f NODE_SERVER_0 // 잘지워졌나 확인하고  docker ps -a 잘 지워집니다.//0.0.2 버젼 이미지로 컨테이너를 다시 생성합니다.  docker create --name NODE_SERVER_0 -p 3000:3000 node_server:0.0.2   //서버를 실행합니다. docker start NODE_SERVER_0 잘 실행됩니다.이제 다시 접속해봅시다.안녕! 나 지금 Docker 안에 있어!이제 Docker로 여러 개의 서버를 띄우겠습니다. NodeJS는 싱글 스레드이기 때문에 하나의 CPU를 여럿이 나눠 갖는 건 비효율적입니다. 따라서 CPU 숫자에 맞춰서 서버를 띄워보겠습니다.제 맥북엔 CPU가 4개뿐입니다.CPU수에 맞춰 추가로 생성하기추가로 컨테이너를 생성하고, 서버를 실행합니다. 서버 목록도 확인해야겠죠.서버 생성서버 실행서버 목록 확인포트번호는 같은 포트를 쓸 수 없기 때문에 3001, 3002, 3003으로 매핑합니다. 브라우저로 접속해서 확인해보겠습니다.각 포트별 접속 화면미리 만들어둔 이미지 덕분에 서버 3대를 띄우는 데에 5분도 안 걸렸습니다. 하지만 Docker 서버를 여러 개 띄워도 결국 사람의 손이 닿아야 합니다. 따라서 이번에는 NodeJS의 Cluster를 활용해 적은 수의 Docker Container를 이용하면서도 다수의 CPU를 사용하겠습니다. 또 죽은 워커를 다시 살려 서버가 다운되는 것을 막아 안정적인 서비스도 구축해보겠습니다.4. 멀티코어대응 NodeJS Cluster 구성2컨테이너용 NodeJS Cluster서버 어플리케이션 작성하기var cluster = require('cluster'); var os = require('os'); var uuid = require('uuid'); const port = 3000; //키생성 - 서버 확인용 var instance_id = uuid.v4();  /**  * 워커 생성  */ var cpuCount = os.cpus().length; //CPU 수 var workerCount = cpuCount/2; //2개의 컨테이너에 돌릴 예정 CPU수 / 2  //마스터일 경우 if (cluster.isMaster) {     console.log('서버 ID : '+instance_id);     console.log('서버 CPU 수 : ' + cpuCount);     console.log('생성할 워커 수 : ' + workerCount);     console.log(workerCount + '개의 워커가 생성됩니다\n');        //CPU 수 만큼 워커 생성     for (var i = 0; i < workerCount>         console.log("워커 생성 [" + (i + 1) + "/" + workerCount + "]");         var worker = cluster.fork();     }        //워커가 online상태가 되었을때     cluster.on('online', function(worker) {         console.log('워커 온라인 - 워커 ID : [' + worker.process.pid + ']');     });        //워커가 죽었을 경우 다시 살림     cluster.on('exit', function(worker) {         console.log('워커 사망 - 사망한 워커 ID : [' + worker.process.pid + ']');         console.log('다른 워커를 생성합니다.');                 var worker = cluster.fork();     });  //워커일 경우 } else if(cluster.isWorker) {     var express = require('express');     var app = express();     var worker_id = cluster.worker.id;         var server = app.listen(port, function () {         console.log("Express 서버가 " + server.address().port + "번 포트에서 Listen중입니다.");     });        app.get('/', function (req, res) {         res.send('안녕하세요 저는 워커 ['+ cluster.worker.id+'] 입니다.');     });  } CPU 숫자를 받아 CPU 수(4)를 컨테이너 수(2) 로 나눠 워커를 생성하는 NodeJS 클러스터 구성입니다. 이렇게만 해도 운영에는 무리가 없지만 컨테이너 2개의 구분이 안 되서 확인할 수가 없습니다.그러므로 마스터와 워커의 통신을 이용해 마스터의 uuid를 얻겠습니다. (워커와 마스터 간의 데이터 이동은 통신 말고는 메모리DB 등의 데이터 저장소밖에 없습니다)마스터의 아이디를 알아오는 로직이 추가된 어플리케이션 작성var cluster = require('cluster'); var os = require('os'); var uuid = require('uuid'); const port = 3000; //키생성 - 서버 확인용 var instance_id = uuid.v4();  /**  * 워커 생성  */ var cpuCount = os.cpus().length; //CPU 수 var workerCount = cpuCount/2; //2개의 컨테이너에 돌릴 예정 CPU수 / 2  //마스터일 경우 if (cluster.isMaster) {     console.log('서버 ID : '+instance_id);     console.log('서버 CPU 수 : ' + cpuCount);     console.log('생성할 워커 수 : ' + workerCount);     console.log(workerCount + '개의 워커가 생성됩니다\n');         //워커 메시지 리스너     var workerMsgListener = function(msg){                    var worker_id = msg.worker_id;             //마스터 아이디 요청             if (msg.cmd === 'MASTER_ID') {                 cluster.workers[worker_id].send({cmd:'MASTER_ID',master_id: instance_id});            }      }        //CPU 수 만큼 워커 생성     for (var i = 0; i < workerCount>         console.log("워커 생성 [" + (i + 1) + "/" + workerCount + "]");         var worker = cluster.fork();                //워커의 요청메시지 리스너         worker.on('message', workerMsgListener);     }        //워커가 online상태가 되었을때     cluster.on('online', function(worker) {         console.log('워커 온라인 - 워커 ID : [' + worker.process.pid + ']');     });        //워커가 죽었을 경우 다시 살림     cluster.on('exit', function(worker) {         console.log('워커 사망 - 사망한 워커 ID : [' + worker.process.pid + ']');         console.log('다른 워커를 생성합니다.');                 var worker = cluster.fork();         //워커의 요청메시지 리스너         worker.on('message', workerMsgListener);     });  //워커일 경우 } else if(cluster.isWorker) {     var express = require('express');     var app = express();     var worker_id = cluster.worker.id;     var master_id;        var server = app.listen(port, function () {        console.log("Express 서버가 " + server.address().port + "번 포트에서 Listen중입니다.");     });        //마스터에게 master_id 요청     process.send({worker_id: worker_id, cmd:'MASTER_ID'});     process.on('message', function (msg){         if (msg.cmd === 'MASTER_ID') {             master_id = msg.master_id;         }     });        app.get('/', function (req, res) {         res.send('안녕하세요 저는 ['+master_id+']서버의 워커 ['+ cluster.worker.id+'] 입니다.');    });  } Docker Container에 올리기 전 로컬 테스트를 먼저 진행합니다. 서버 구동!두 개의 워커가 실행되었습니다.똑같은 localhost:3000번 접속이지만 워커의 번호가 다릅니다.이제 워커로 CPU 수만큼 워커를 생성할 수 있게 되었습니다. 이제 워커가 어떻게 안정적으로 서비스되는지 테스트하겠습니다. 워커 킬링 테스트하기워커 킬러 로직 작성//워커 킬링 테스트     app.get("/workerKiller", function (req, res) {         cluster.worker.kill();         res.send('워커킬러 호출됨');     }); 실험에 앞서 똑같은 상황 재연 마스터 아이디를 유심히 봐주세요. 워커 킬러를 실행하겠습니다.워커 킬러 호출아래는 호출된 결과입니다. 하나의 워커가 죽자마자 곧장 다른 워커가 태어나(?) 3000번을 Listen하기 시작했습니다. 워커 킬러가 호출된 화면이제 워커 킬러를 여러 번 호출해보겠습니다. CMD+R을 꾸욱 눌러 연속으로 킬링해봤는데 아래 화면처럼 바로 살아납니다.접속해서 현재 워커를 확인합니다.위의 화면처럼 마스터의 UUID가 그대로인데 워커만 교체되었습니다. 준비는 끝났습니다. 이제 Docker를 이용해 2명의 워커를 가진 2개의 NodeJS서버를 실행하고, 4개의 귀여운 CPU를 불살라봅시다! 5. Docker로 NodeJS Cluster 서버 실행하기docker build --tag node_server:0.0.3 /Users/kww/eclipse-workspace/nodejs-for-article docker create --name NODE_SERVER_0 -p 3000:3000 node_server:0.0.3 docker create --name NODE_SERVER_1 -p 3001:3000 node_server:0.0.3 docker start NODE_SERVER_0 docker start NODE_SERVER_1 cluster가 적용된 2개의 컨테이너 start0.0.3번 이미지로 생성된 2개의 컨테이너 서버가 무사히 로드되었습니다. 이제 접속해서 확인해볼까요?cluster가 적용된 2컨테이너 4서버 구동화면WOW! 2개의 URL, 2개의 UUID, 각 2명의 워커까지. 완벽한 2.2.2입니다. 마치 홍진호를 보는 듯한 서버 현황입니다. 이제 워커 킬러로 습격해보겠습니다.워커 킬러 습격 후위의 이미지를 보면 3000번 포트서버에서 13명, 3001번 포트서버에서 22명의 워커가 사망했습니다. UUID를 통해 2개의 서버에서 일정량의 워커가 매우 안정적으로 서버를 지키고 있는 걸 알 수 있었습니다.지금까지 2개의 컨테이너로 4개의 서버를 구성해보았습니다. CPU 숫자와 나눠지는 수에 따라 컨테이너의 수, NodeJS 클러스터 서버의 수를 유동적으로 조정할 수 있습니다. 전에 운영하던 API서버는 16코어 서버였고, 로드벨런서 및 기타 작업용 1코어의 여분을 남기고 15코어 / 3 으로 5개의 워커를 가진 3개의 NodeJS서버를 도커 컨테이너로 운영했었습니다.여기서 문제점이 생깁니다. 우리는 어떤 서비스를 할 때 하나의 도메인을 쓰는데 포트번호가 2개죠? 어떻게 해야 할까요. 여기서 바로 한참을 기다렸던 불곰국의 Nginx가 등장합니다.6. Nginx로 로드밸런싱 하기Nginx은 “더 적은 자원으로 더 빠르게”를 지향합니다. 러시아의 이고르 시쇼브(Игорь Сысоев)는 Apache에서 10,000개의 접속을 동시에 다루기 힘든 걸 해결하려고 Nginx를 개발합니다.Nginx는 NodeJS와 유사하게 싱글 스레드 방식에 이벤트 드리븐 구조 사용하는 오픈소스 HTTP서버로 최근 아파치의 점유율을 상당히 뺏고 있는 서버입니다. 다운로드 링크를 아래에 써두었습니다.Nginx 설치WindowNginx 다운로드Macbrew install nginx Linuxapt-get install nginx or yum install nginx Nginx 설치 성공Nginx 기본 접속 화면서버 조작방법서버 시작 : nginx 서버 중지 : nginx -s stop 서버 재시작 : nginx -r reload (맥에선 이건 안되는듯?) 기본 설정은 8080포트로 되어있습니다. 원하는 포트르 로드벨런싱 설정을 해보겠습니다. Nginx 로드밸런싱 설정아래는 Nginx의 로드밸런싱입니다.#http블럭 내부에 추가     #NodeJS 서버 로드밸런싱     upstream nodejs_server {         #least_conn;         #ip_hash;         server localhost:3000 weight=10 max_fails=3 fail_timeout=10s;         server localhost:3001 weight=10 max_fails=3 fail_timeout=10s;     }        #3333번 포트 NodeJS 서버로 연결     server{         listen               3333;         server_name  localhost;                location / {             proxy_pass http://nodejs_server;         }     } 로드밸런싱이 잘 적용되었는지 확인해보겠습니다. 로드밸런싱 적용 이후모든 브라우저에서 3333번으로 접속했는데 서로 다른 2개의 서버가 번갈아 접속되고, 워커가 가끔 바뀌는 걸 확인할 수 있습니다. 이번엔 로드밸런서로 워커 킬러를 호출하겠습니다.로드밸런싱 포트인 3333번 포트로 여러 번 호출결과 확인Nginx 로드밸런서가 확실하게 작동하는 걸 확인할 수 있었습니다. 위의 이미지에서 서버가 자꾸 바뀌는 모습을 볼 수 있는데, 이는 세션이 유지되지 않기 때문입니다. 실제 서비스에서는 세션의 유지를 위해 ip_hash 옵션이 꼭 필요합니다.ip_hash : 동일한 IP의 접속은 같은 서버로 접속하도록 하는 옵션입니다.  least_conn : 가장 접속이 적은 서버로 접속을 유도하는 옵션으로 ip_hash와 같이쓰입니다. Conclusion자, 고생하셨습니다. 여기까지 Docker와 NodeJS, Nginx를 이용해 관리하기 쉽고, 일부러 죽여도 죽지 않는 안정적인 서비스 환경을 구축해봤습니다. 한 가지 주의할 점이 있습니다. NodeJS의 Cluster는 죽은 워커를 바로 살리는데 싱글스레드여서 그런지 그 속도가 정말 어마어마합니다. 따라서 NodeJS Cluster를 사용할 땐 여러 핸들링에 신중하세요. 모든 promise에 반드시 catch를 달아 핸들링하고, 오류가 날 것 같은 로직엔 반드시 try - catch를 달아 핸들링을 해야 합니다. 그렇지 않으면 다시 살아나는 워커에 의해 서버의 자원이 고갈될 수 있습니다.예전에 16코어 서버를 운영할 땐 서버 자원에 비해 사용자가 적어서..(눈물) 5워커 2개의 서버만 구동하고 여유를 두었습니다. 그리고 서버 패치가 있을 때 3번째 서버를 대기시켰습니다. 앱에서 업데이트가 완료되는 시점에 Docker Container를 바꿔치기 하는 방식으로 Non-Stop서비스를 운영했죠. 혹시 코어가 빵빵한 여유 서버가 있는데 재빠르고 좀비 같은 서비스를 구성해야 한다면 위와 같은 환경 구축을 강력히 추천합니다. 지금까지 긴 글을 읽어주셔서 감사합니다.ps. 글 쓰다 보니 해가 떴네요. 하하.참고1) 가상 머신은 작은 이미지라도 기가바이트 단위의 사이즈와 Load되기까지 상당한 시간이 소요된다.2) 그러나 Windows의 경우, Hiper-v위에 리눅스를 띄워 도커를 구동한다. Mac에서도 가상 머신 위에서 구동된다. 따라서 성능적인 강점은 리눅스에만 적용된다.3) 도커에서는 NAME 속성을 지어주지 않으면 알아서 이름을 지어주는데 romantic한 단어가 많다.글강원우 과장 | R&D 개발2팀[email protected]브랜디, 오직 예쁜 옷만#브랜디 #개발팀 #개발자 #개발환경 #업무환경 #인사이트 #경험공유

기업문화 엿볼 때, 더팀스

로그인

/