'개발자세상'에 해당되는 글 103건

  1. 2023.10.06 Scala future/blocking
  2. 2023.03.10 deb packaging , postinst
  3. 2022.03.31 Rate Limit
  4. 2020.07.01 [도서리뷰]엔터프라이즈 자바 마이크로 서비스
  5. 2018.10.30 Kotlin
  6. 2018.06.09 Chronos Notification issue
  7. 2017.12.20 Apache 2.0, PHP 7.0 and Ubuntu
  8. 2017.11.28 POI로 Pivot테이블 만들기
  9. 2017.07.16 Java 8 , Reactive
  10. 2017.06.03 Mobile세상 ....

늘 휴가를 가면 뭔가 이슈가 터진다.
이번 여름도 오랜만에 머리 식히려, 회사 이메일 다 무시하고 1주일 쉬고 왔는데, 
와서 체크해보다보니 creative unexpiration script가 일주일간 실행되지 않아 bidding 결과가 떨어 지는 일이 생겼다.
하필 휴가 출발하는 첫날 실행되던 Job이 vertica DB resource 이슈로  DB Connection 을 생성하지 못했는데, 
또 하필 그 Job이 Terminate 되지 않고 Hang up되어 그대로 Schedule 이 멈춰버린 것 이었다.

일단 어찌저찌 수습을 했지만, 이번엔 Tech Support 에서도 꽤 심하게 반응을 해서 Monitoring 방법을 찾아 보게 되었다.

다행히 최근에 Kubernetes 에서 Prometheus 를 통한 metrics를 구현 하게 되어 이 Job도 그렇게 해보기로 생각해 보았다.
docs/content/docs/instrumenting/exposition_formats.md at main · prometheus/docs (github.com)

문제는 CronJob 에 대해서도 Prometheus가 metrics 를 지원하냐 인데 prometheus 관련 annotation을 넣었더니 metrics  end-point를 1분 마다 hitting하는것은 확인이 된다.
그럼 1분 동안의 데이터를 유실할 수 있는 문제가 생기는데, 우리는 Job이 실행되는 거만 체크하려는 거니깐 1분 데이터 정도는 큰 문제가 되지 않을 듯 싶었다. 다만 전에는 모든 처리가 끝나고 메일 보내기 전에 metrics count를 set하게 되어 있었는데, 이걸 매번 creative processing할 때 metrics 를 update 하도록 변경해야 하였다.

당연히 문제 없이 될 줄 알았는데... 이게 Job 시작할 때 50 정도 까지 Counting을 하고 바로 Counting이 되지 않는 거다.
코드를 봐도 문제가 없고, 로그를 보면 Prometheus 가 metrics end point도 잘 hit하는게 보인다.

이게 무슨 문제일까 싶어서 metrics count method에서 로그를 찍게 해보니 Cronjob이 끝날때쯤에 갑자기 count method가 집중적으로 찍히는게 보인다.

이게 무슨 일일 까 싶었는데... 찾아 보니 future에 map을 사용할 경우 같은 future내의 connected processing이 되는 게 아닌 또 다른 future 객체가 생성되어 map operation이 수행되는 것이다.
내 local 환경에서는 map을 써도 단일 thread내에서 처리되듯이 큰 문제 없이 수행이 되는데..
서버에만 가면 metrics 의 count method를 위한 map processing을 처음 50개 정도는 바로 진행하지만 그 이후는 모두 wait 하였다가 cronjob이 끝날 때 한꺼번에 처리 해서 생긴 문제였다.
생각해보면 metrics count같은 method를 매번 처리 하는 것 보다 한번에 몰아서 처리하는 게 성능상으로는 더 좋을 것 같다는 생각이 든다.

어쨋든.. future.map을 이전 process 이후 바로 실행하게 하려고 찾아보다보니 blocking을 사용하면 전체 processing를 하나의 thread로 묶어서 처리 할 수 있게 되어 있다.

Understanding Scala Futures and Execution Contexts – Beyond the lines

 

Understanding Scala Futures and Execution Contexts – Beyond the lines

Viktor Klang recently published a set of useful tips on Scala Futures. While being widespread and heavily used, people (especially newcomers) are still experiencing problems working with Scala Futures. In my opinion many of the problems come from a misunde

www.beyondthelines.net

늘 느끼는 거지만 future가 개념 잡기도 어렵지만 사용하기도 참 어려운 기술이라는 생가이다.
아니면 아직도 예전 blocking 기반의 기술 에서 벗어나지 못해서 인걸 수도 있겠다.

'개발자세상 > 자바세상' 카테고리의 다른 글

Chronos Notification issue  (0) 2018.06.09
POI로 Pivot테이블 만들기  (0) 2017.11.28
Scala  (2) 2016.06.16
Mockup 테스트  (0) 2016.02.02
java.lang.OutOfMemoryError: unable to create new native thread  (0) 2015.08.15
Posted by headiron
,

Dawid 이 퇴사한 후 떠 안은 시스템 중 하나가 geo-manager 이다.
IP -> geo resolution service를 제공하는 3rd Party data를 messaging해서 회사 시스템에 Inject하는 시스템이다.

근데, 3rd Party 의 IP coverage가 증가함에 따라 Data Size 가 증가하는데..
그 동안은 주로 데이터를 Inject한 회사 시스템 메모리 사용량을 주로 챙겨보고 있었는데..
지난 주에 새로운 패키지를 Baking 하려다 보니

deb package Install 후 data curruption 되었다는 에러가 나고 Puppet 실행이 fail 하는 문제가 생기기 시작했다.
Sys Admin이 error를 체크 하더니 data file이 8G가 넘어서 deb package 에서 처리를 못해서 생기는 문제라고 한다. :-(  
https://www.gnu.org/software/tar/manual/html_section/Formats.html

 

그러면서 제시해준 해결책이 파일 사이즈를 줄여라...
Puppet Log를 보면서 파일이 1.8G 정도 밖에 되지 않아서 좀 이상하다 싶었는데..
실제로 파일을 gzip으로 압축을 했더니 8G 가 1.8G로 줄어 드는 놀라운 매직(?)이 발생했다.

흠.. 일단 deb packaging에 들어가기 전에 파일을 gzip으로 compress하고, 
deb package 설치 후에 파일 압축을 해제 하면 될 것 같은데.
문제는 그러면 다른 팀 Engineer에게 boot code를 수정하라고 해야 하고..
어쨋든 해당 상황을 공유했더니 postinst/ prerm을  package에 추가 하라는 의견이 나왔다.

찾아 보니

deb 설치 이전/이후에 실행되는 Script들이 pre/postinst 이고,
pre/postrm은 deb package 이외에 cleanup이 필요한 파일들을 설치 이전/이후에 정리해주는 script들이다.

그리고 이 script들은 step 에 맞추어 각 parameter에 맞추어 실행이 되는 것이다.
https://askubuntu.com/questions/101962/how-to-run-a-script-only-during-first-install-of-a-package-and-not-during-upgrad

 

How to run a script only during first install of a package and not during upgrades?

I recently started packaging up some of my software and publishing it on Launchpad. The installation and removal works fine, but upgrading the package from one version to the next version is proble...

askubuntu.com


우리 같은 경우는 일단 postinst.sh 가 필요하고 package가 정상적으로 설치 된 이후에만 실행이 되어야 하기에

첫 번째 파라미터가 configure 일 경우에만 실행이 되도록 작성을 하였다.

#!/bin/bash

set -e

case "$1" in 
      configure)
      .....
esac

exit 0


테스트를 진행해 보니 일단 package가 설치가 되면 해당 script들은 
/var/lib/dpkg/info/패키지이름.postinst 와 같이 저장이 된다.

 

https://www.debian.org/doc/debian-policy/ap-flowcharts.html
그리고 위에 사이트에 있는 그림들 처럼 현재 버전 , 설치 중 버전의 script들을 각 상황에 따라 실행을 하게 된다.

e.g prerm은 이전 설치 버전의 script로 버전 파라미터는 설치 할 버전 ,
      preinst는 설치 하는 버전 package script로 버전 파라미터는 현재 버전으로.

잘 될지는 몇 일 간의 테스트로 결정이 될 듯 한데.
기본적인 테스트에서는 큰 문제는 발견할 수 없었다.

주로 Java/Scala를 사용하고,
docker를 사용한 Cloud 위주로 작업하는 요즈음.. deb packaging을 사용할 일이 앞으로 있을지는 모르지만.
어쨋든 뭐 하나를 또 배운 그런 요즈음 이다.

'개발자세상' 카테고리의 다른 글

Rate Limit  (0) 2022.03.31
[도서리뷰]엔터프라이즈 자바 마이크로 서비스  (0) 2020.07.01
Kotlin  (0) 2018.10.30
Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Java 8 , Reactive  (0) 2017.07.16
Posted by headiron
,

Rate Limit

개발자세상 2022. 3. 31. 03:28

지난 2년간 Main으로 했던 일이 , Google의 DSP서비스인 DV360와 TTD API integration이었다.

Integration script를 계속 관리해오고 있었지만, 새로운 Integration을 진행한 건 처음인 것 같다.

 

일단 계속 integration account를 늘려오면서 성능 이슈가 많이 발생해서
( 특히 DV360는 Client Library를 제공하는데.. 이게 Concurrent를 고려하지 않고 개발되었다.)

수정을 해왔는데.. 어느 순간엔가 갑자기 TTD integration script가 느려진게 보인다.

 

마침 여유가 생겨 체크해보니 Data pulling하는 중에 Rate Limit으로 Pulling이 Fail 하면서 벌어지는 일이었다.

Thread도 조절해보고 PageSize도 조절해 봐도 해결이 잘 안되서 마지막으로 internet search를 해보니 

딱 내 상황에 맞는 Article이 나온다. 더군다나 Scala 코드...

 

https://itnext.io/handling-rate-limits-with-scala-futures-8904538bca7f

 

Handling Rate-Limits with Scala Futures

Slow down while going fast to go faster.

itnext.io

읽다가 저자 얼굴을 보니 작년에 다른 회사로 이직한 John 이다.

 

회사에서 종종 seminar도 진행하고 글도 많이 쓰는 건 알고 있었지만 

오랜만에 글로 보니 반갑고.. 뭐 그렇다. :-) 

 

어쨋든 오랜 친구(?)의 조언 덕분에 Rate Limit 이슈는 해결이 되는데..

 

나도 가끔은 이런 기술적인 Blog도 좀 작성하고 해야 하지 않나 하는 생각이 좀 든다..

'개발자세상' 카테고리의 다른 글

deb packaging , postinst  (0) 2023.03.10
[도서리뷰]엔터프라이즈 자바 마이크로 서비스  (0) 2020.07.01
Kotlin  (0) 2018.10.30
Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Java 8 , Reactive  (0) 2017.07.16
Posted by headiron
,

어쩌다 보니 이번달에도 한빛 미디어 도서 리뷰 이벤트에 참여하게 되었다.

개인적으로는 안드로이드 개발 관련 도서를 리뷰하고 싶었는데... 해당 도서는 E-Book을 출간하지 않는 단다..

인기있는 책이 E-Book으로 만들었다가 사람들 한테 풀리면 좀 타격이 있을 수 있으니 그럴 수 있겠다 싶어 이해는 하는데..

그래도 대부분의 원어권 출판사들은 E-Book을 같이 출간하는 상황을 보면 좀 아쉽기는 하다.

뭐 달리 생각하면 한국 시장이 작아서 그런 것이니 이해를 해야 하지 않을까 ...

 

어쨋든.. 이미 회사에서 사용하는 마이크로 서비스를 과연 다른 쪽은 어떻게 사용할 까 싶어서 이 책을 대신 리뷰하기로 했는데 

꽤 괜찮은 선택인 듯 싶다.,

 

일단 책 자체가 꽤 잘 쓰여 졌다. 

단순히 이론만 나열하는게 아니라 실제 Framework 코딩 방법을 자세히 설명하고 있어서 마이크로 서비스를 구축하는 실무자들에게는 꽤 괜찮은 입문서가 될 수 있을 것 같았다.

 

시간 부족으로 ( 다른 때 처럼 월말에 리뷰를 끝내야 하는 줄 착각해서.. ) 실제 코드를 직접 돌려 보지는 못했는데

전체적인 설명을 보면 큰 무리없어 테스트 가능할 것 같았다.

 

다만 번역을 진행하면서 지나치게 많은 단어를 한글화 해서 조금 아쉬운 부분이 보였다.

특히나 Framework 이나 App 이름은 영문 이름 그대로 남겨놓았으면 어떨까 싶었다.

 

그래도 전체적인 번역도 비교적 깔끔한 느낌이다.

 

 

'개발자세상' 카테고리의 다른 글

deb packaging , postinst  (0) 2023.03.10
Rate Limit  (0) 2022.03.31
Kotlin  (0) 2018.10.30
Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Java 8 , Reactive  (0) 2017.07.16
Posted by headiron
,

Kotlin

개발자세상 2018. 10. 30. 22:39

구글에서 안드로이드 공식 지원언어도 Kotlin을 지정한지도 벌써 2년 가까이 되었다.


그동안 볼 기회가 없었는데 Phily JUG에서 Kotlin을 소개한다고 해서 참여해 보았다.


뭐.. 소개하는 자리니깐 아예 모르고 가도 될테지만 그래도 너무 모르고 가면 그럴 듯해서 조금 찾아 보고  가 보았는데 Swift 가 Kotlin의 영향을 받았다나 어쨋다나..


Meetup에 가서 하나씩 들여다 보니 대 부분의 내용이 Scala에 있는 내용들이다. 

몇 몇 Java만 해왔던 사람들은 이해가 되지 않는 듯 조금은 기초적인 질문을 하는데 

Scala에 있는 개념을 대입해 보니 대 부분이 이해가 간다.


예전에 자바 세계에만 빠져 있을 때는 자바 밖의 세상은 보이지 않았는데 

자바 밖에서는 많은 언어들이 만들어지고,서로에게 영향을 주며 발전해 오고 있었다.

247에 있을 때는 그걸 모르고 자바에만 메몰되어 있었는데 , 

어거지로 라도 Scala를 보게 되면서 얼마나 갇혀 살았었나 싶었다.


최근에 접한 언어들 중에 개념이 조금 다른 언어는 Go 정도 이지 않나 싶다.

아직은 보지 않았지만, Rust가 비슷한 목표로 만들어지 언어이다 보니 공부해보면 또 좀 비슷하지 않을 까 싶다. 


하.. 참 공부할 것들은 많아 지는데 시간은 정해져 있고...

  


'개발자세상' 카테고리의 다른 글

Rate Limit  (0) 2022.03.31
[도서리뷰]엔터프라이즈 자바 마이크로 서비스  (0) 2020.07.01
Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Java 8 , Reactive  (0) 2017.07.16
Mobile세상 ....  (0) 2017.06.03
Posted by headiron
,

AppNexus 업무로 넘어 온 후 제일 먼저 했던 일이 Chronos 도입이었다.


OAS하면서 EJB Java코딩만 하던 나에게 완전 환경이 다른 AppNexus환경에서 해당 업무를 해내는 건 정말 골치 아픈 일이었다.도입한 이후로 몇가지 문제가 생겨도 그냥 Internet searching해서 대충 문제 봉합하는 정도..


얼마전에 구글에 등록된 퇴사자 계정을 Disable한 이후로 Chronos에 등록된 모든 Script가 동작하지 않는 문제가 발생했다.

내가 주기적으로 모니터링 하고 있었기에 크게 이슈화 되기 전에 문제를 해결했는데,

근본적으로는 Script 가 Fail했을 경우에 Notification해줬으면 금방 알 수 있었던 문제 이다.


일단 예전에 Chronos에 메일을 보내게 할려면 /etc/chronos/conf 폴더에 mail_server라는 파일을 만들고 해당 파일에 파일 서버명을 적으면 된다는 Article 을 보고 적용했던 일이 생각났다.ps java로 command를 확인해 보면 mail_server option 이 parameter로 잘 적용된 것도 보인다.


우선 Log를 Enable시켜 놓고, 메시지를 확인하면서 Chronos 소스 코드를 확인해 보았다.


chronos script를 확인해 보니 /etc/chronos/conf 폴더에 option이름으로 파일을 만들고 값을 저장하면 해당 옵션을 자바 구동시 넣어 주는 것을 확인했다.결국 ps 로 확인했다고 해서 option이 제대로 적용됐다는 보장이 없는 것이다.


결국은 Chronos 소스를 봐야 할 문제 ...

소스를 Checkout 해보니 언어는 Scala.. ( 예전에 한 참 Chronos일 할 때 Scala로 개발했다는 얘기를 들을 기억이.. )


예전에는 Scala 를 몰라 뜨아 하고 덮었을 텐데 다행히도 AppNexus 업무를 맡은 후 공부를 해 놔서 걱정이 없다.


소스를 보면서  mail_server가 정확한 option인건 확인을 했고,

Module class에서 @Singleton, @Provides Annotation으로 notification actor를 Initial 해주는 것도 확인이 되었다.


좀더 자세히 뒤져 보았더니 

메일 관련 Config중 

mail_server config는 <Server Address>:<Server Port>로 설정이 되어 있어야 하고,

mail_from 이 String으로 Define되어 있어 반드시 입력이 되어 있었어야 하는 것이었다.


결국 /etc/chronos/conf 폴더에 mail_server는 <Mail Server Addr>:25, mail_from은 우선 내 메일 주소를 넣어 보니 메일이 잘 온다.


Scala를 좀 뜯어 볼 줄 알았다면 일찌감치 해결 했을 문제를 2년 동안 전전 긍긍했던 것이다. :-(


오늘도 이렇게 지식의 힘들 느끼며 문제를 해결했다.



이슈를 추적하면서 한가지 궁금했던게...

대체 Chronos 소스가 어디 있는 건가 하는 문제였는데 ...


Script 를 따라 가다보니 /usr/bin/chronos가 실행 Script이고, 

파일을 열어 보니 윗 부분은 Schell script가 아랫부분은 Binary 코드가 있다.


좀 이상해서 검색 해보니 cat을 이용하여  schell script와 jar파일을 다른 File에 redirect하고 x permission을 주면 Shell script와 jar를 한 파일로 만들 수 있는 것이다.

https://coderwall.com/p/ssuaxa/how-to-make-a-jar-file-linux-executable


그리고 Chronos log  enable은 log4j 파일을 작성한 후 

/usr/bin/chronos 의 구동 부분에 -Dlog4j.configuration=file:/etc/chronos/log4j.properties 와 같이 옵션을 추가 하면 된다.


요즘 Docker+ Kubernates 가  Popular해서 Mesos+Chronos 가 밀리고 있는데 

2년 전에 Chronos 도입할 떄 내가 좀 더 기술적으로 잘 알았으면 

적어도 AppNexus에서는 좀 더 각광받는 기술이 되지 않았을 까 하는 생각이 들고 

언제는 기술적으로 준비가 되어 있어야겠다 하는 생각이 많이 든다. 






'개발자세상 > 자바세상' 카테고리의 다른 글

Scala future/blocking  (0) 2023.10.06
POI로 Pivot테이블 만들기  (0) 2017.11.28
Scala  (2) 2016.06.16
Mockup 테스트  (0) 2016.02.02
java.lang.OutOfMemoryError: unable to create new native thread  (0) 2015.08.15
Posted by headiron
,

강하게 Driving하던 Project가 구글쪽 API Issue 이슈로 Holding되고 말았다.


마침 연말이고 해서 특별히 진행되는 프로젝트도 없고 ( 뭐 사실 나는 혼자 프로젝트 한다...  24/7에서 어느 순간 부터 혼자 일하게 되더니 근 10년 넘게 이런 상태.. -.- ) 해서 결국 예전에 준비 했던 Chronos 시스템을 Ubuntu로 Porting하는 프로젝트를 Assign 받게 되었다.


우리팀에 처음 Assign되서 진행했던 프로젝트가 Chronos 프로젝트 였다.

당시 Ubuntu로 진행해 달라고 했는데 ... Reference도 없고 해서 어쩔 수 없이 CentOS에서 진행했는데..

2년 가까이 지나고 나니... 대부분의 System  시스템들이 Ubuntu 로 Porting해서  Reference도 많아 져서 비교적 손쉽게 진행할 수 있었다.


예전에 문제가 되었던 부분이 PHP 였는데 API가 Ubuntu로 Porting되면서 비교적 손쉽게 진행할 수 있었다.


근데 Apache2.0, PHP 7.0가 되면서 Config Structure가 많이 바뀌어서 많이 햇갈리게 되었다.


일단 Apache Config Directory가 /etc/apache2로 되고,하위에 

conf-available , conf-enabled

mods-available , mods-enabled

sites-available, sites-enabled

와 같은 Folder들이 생성되었다.


예전에는 httpd.conf에 필요한 모듈들에 대한 Direction을 Define하는 식이었는데 

이제는 a2enmod , a2query command를 이용해서 Module을 Enable하면 mods-available에 있는 설정이 mods-enabled 폴더에 Symlink로 연결되고 기본 conf 설정이 추가 되는 방식이다.


/usr/sbin/a2query -q -m proxy_http && /usr/sbin/a2query -q -m status && /usr/sbin/a2query -q -m headers


/usr/sbin/a2enmod -q proxy_http status headers


예전에 한 파일 ( 물론 폴더 include하는 방식도 있었지만 ) 에 Direction 을 적는 방식에 비해 꽤 편해진 느낌이다.


그리고 Mesos Master UI detection을 위해 

특정 Direcoty를  Aliasing하고  index.php를 사용했었는데 

 

Require all granted 

를 Apache conf에 추가해 줘야 잘 동작이 된다.


https://stackoverflow.com/questions/11215283/alias-403-forbidden-with-apache


요즘은 HTTP 1.1도 있고 해서 Apache를 좀 안쓰려고 하는데 

오랜만에 생소한 버젼으로 하려니 이런 저런 문제가 생기게 된다..


그나저나 왜 Ubuntu로 시스템을 변경하나 싶은데..

요즘 Docker를 좀 보다보디 Docker 때문인듯 싶다.


뭐. 덕분에 Docker도 공부하고... :-) 

'개발자세상' 카테고리의 다른 글

[도서리뷰]엔터프라이즈 자바 마이크로 서비스  (0) 2020.07.01
Kotlin  (0) 2018.10.30
Java 8 , Reactive  (0) 2017.07.16
Mobile세상 ....  (0) 2017.06.03
JavaScript polling  (0) 2017.03.17
Posted by headiron
,

POI를 써 온지는 꽤 오래 되었다. 주로 테이블 데이터를 엑셀 파일로 만드는 정도를 했는데  생각해 보면 그런 기능 정도는 그냥 csv 파일을 만들어도 되는 기능이었던것 같다.


AppNexus Join이후로는 통계 관련 요구사항이 없어 쓸 일이 없었는데 

얼마전에 Carrier Data Integration 모듈(?)을 개발하면서 

Data refresh전에 데이터 변경 내역을 보여주는 Excel을 만드는 게 어떨까 해서 Excel을 만들어 보았는데 

생각해 보니 이 기능을 실제 Integration Module 에 넣는게 어떨까 해서 다시 POI를 쓰게 되었다.


제일 중요한게 Pivot 테이블 생성 기능인데 

마지막으로 POI를 사용할때는 Pivot 기능이 없었던걸로 기억하는데 다행이 Pivot 테이블 생성하는 기능도 추가가 되었다.


다만 Pivot기능을 사용하기 위해서는   poi이 외에 poi-ooxml도 library에 추가해 주어어 햔다.

"org.apache.poi" % "poi" % "3.17",
"org.apache.poi" % "poi-ooxml" % "3.17",

이렇게  poi와 poi-ooxml을 추가한 후 Excel Sheet를 생성해서 데이터를 해당 Sheet에 저장했다.


val wb = new XSSFWorkbook
val sheet = wb.createSheet("Rawdata") IPRanges.foreach(ipRange => { val row = sheet.createRow(rowIndex) row.createCell(0).setCellValue(ipRange("country").asInstanceOf[String]) ... row.createCell(6).setCellFormula(s"F${rowIndex + 1}-E${rowIndex + 1}+1") rowIndex = rowIndex + 1 })

이렇게 데이터를 생성한 후 Pivot테이블을 위한 Sheet를 생성해서 Pivot테이블의 데이터 영역에 위의 데이터 Sheet를 설정하면 Pivot테이블이 생성된다. val summarySheet = wb.createSheet("Summary") val source = new AreaReference(s"Rawdata!A2:G${rowIndex}", SpreadsheetVersion.EXCEL2007) val position = new CellReference("A3") val pivot = summarySheet.createPivotTable(source, position)

Pivot테이블의 Rows는 아래와 같이 영역내의 몇 번째 Column인지를 지정하면 된다.

pivot.addRowLabel(0) pivot.addRowLabel(1)


Pivot테이블의 Values는 아래와 같이 몇 번째 Column에 어떤 Function 을 적용할지를 지정하면 된다.

pivot.addColumnLabel(DataConsolidateFunction.SUM, 6)


헌데 Pivot테이블의 Columns 부분을 적용할 수 있는 함수를 찾을 수가 없었다.

( 내 Pivot테이블은 국가 , Carrier를 Row로 하고, 데이터에 있는 Before/After 데이터를 Column으로 데이터를 보여 주고 싶은데 이 기능은 Pivot의 Columns 을 통해서 적용이 된다.)


이것 저것 해보다가 안 되서 꽤 오랫동안 Googling을 했더니 아래와 같은 해결 책이 나왔다.


pivot.getCTPivotTableDefinition().getPivotFields().getPivotFieldArray(3).setAxis(
org.openxmlformats.schemas.spreadsheetml.x2006.main.STAxis.AXIS_COL);

pivot.getCTPivotTableDefinition().getPivotFields().getPivotFieldArray(3).addNewItems();
pivot.getCTPivotTableDefinition().getPivotFields().getPivotFieldArray(3).getItems().addNewItem().setT(
org.openxmlformats.schemas.spreadsheetml.x2006.main.STItemType.DEFAULT);

pivot.getCTPivotTableDefinition().addNewColFields().addNewField().setX(3);

데이터 테이블의 3번째 Column의 데이터를 Pivot Table의 Columns에 적용하려면 위에 처럼 몇 개의 함수를 다 선언해야 한다.


구글링하면서 다른 이의 API Naming이 잘못 되었다는 ( addColumnLable-> addValues ) 의견에 전적으로 동의한다.

그리고 왜 Pivot 테이블의 Columns 부분을 저렇게 여러개의 함수를 선언하게 만들었는지 솔직히 이해가 가지 않는다.


뭐... 몇 가지 아쉬움이 있지만 어쨋든 Pivot테이블은 완성이 되었다.


한가지 아쉬운 점은... 엑셀을 오픈하면 Pivot테이블이 있는 Sheet을 Default로 보여주려고 했는데...


wb.setActiveSheet() 으로 Pivot테이블의 Sheet을 적용하면 엑셀 오픈할 때 에러가 발생해서 이 부분은 적용해 주지 못했다.


어쨋든... POI 덕분에 수작업도 줄일 수 있게 되어 뭐.. 기분은 나쁘지 않다.

POI Pivot관련 해서는 아래 페이지들을 참조 했다.

http://www.novixys.com/blog/excel-pivot-table-using-apache-poi/
https://stackoverflow.com/questions/35943812/xssfapache-poi-adding-multiple-column-label-from-single-column-value-in-pivo













'개발자세상 > 자바세상' 카테고리의 다른 글

Scala future/blocking  (0) 2023.10.06
Chronos Notification issue  (0) 2018.06.09
Scala  (2) 2016.06.16
Mockup 테스트  (0) 2016.02.02
java.lang.OutOfMemoryError: unable to create new native thread  (0) 2015.08.15
Posted by headiron
,

Java 8 , Reactive

개발자세상 2017. 7. 16. 14:09

올 봄에 John이 추천해 줘서 알게된 "No Fluff Just Stuff" Conference를 어제 오늘 이틀간 참석하게 되었다.


여러 지역을 돌아다니며 하는 세미나 인데 ,그동안 가고 싶었던 Salt Lake Ciy에서도 진행하기에 덥석 신청해서 오게 되었다.


일단 강사들이 작년에 갔던 Strange Loop에 비해 전문적인 강사들이 주로 진행을 하고


1시간 30분 세션에 한 주제에 대해서 2~3개의 세션을 연이어 진행하다 보니 좀더 많은 것을 배우게 되었다.


주제는 Java 8 , Front-end tech, Machine Learning, Spring 등 다양한 주제 였는데 


첫째날은  Java 8, Docker 둘째날은 Reactive를 중점적으로 들었다.


Java 8같은 경우는 Scala 를 하기 시작하면서 한국 E-Book으로 읽어 보긴 했지만 쉽게 이해가 가지 않았는데 


3개 세션을 들으며 Lambda, Stream 들을 듣고 나니 왜 이렇게 되었는가를 쉽게 이해 하게 되었다.


Kenneth Kousen이 진행했는데 , 책도 많이 저술하고 동영상 강의도 제작 했는데 


집으로 돌아가면 꼭 이분이 저술한 책으로 다시 복습해서 확실히 내껄로 만들어야 겠다 싶다.


Docker의 경우는 두개 세션을 들으며 어렴풋이 개념을 이해하기는 했는데 


너무 내부 적인 부분에 집착하면서 들어서인지 100% 내것으로 소화해 내지는 못한 느낌이다.


하지만 적어도 어떤 기술이고 어떻게 응용되는지에 대해서는 어렴풋이 개념이 잡히는 느낌이다. 


앞으로 회사에서도 Docker를 계속 적용할 예정이니 좀 더 시간을 두고 긴 호흡으로 접근해야 할 느낌이다.


둘째 날은 Reactive에 대해서 중점적으로 들었는데 


얼마전까지 Toby씨가 진행했던 동영상 강의와 Java8 Future관련 내용을 먼저 듣고 들으니 


개념에 대해서는 어느정도 이해 할 수 있었다.


근데 과연 어떤 부분에서 적용해 볼 수 있을 까 하는 생각을 해보니 역시 좀더 공부가 필요할 것 같다.



AppNexus에 Join하고 작년 부터 Conference를 다니게 되면서 들게 되는 생각은 


미국 넘어 온 이후  너무 OAS에 집착하며 스스로를 너무 도태시켜 버렸다는 생각이 든다.


6년이 넘는 시간동안 정말 많은 기술이 나오고, 그런 기술을 배울 수 있는 기회들이 있었는데,


그 기간을 너무 쉽게 보내버렸다는 아쉬움이 든다.


이제라도 따라 가보려고 발버둥 쳐보고는 있는데 


솔직히 언제 다 따라 잡을 수 있을 까 하는 걱정이 많이 든다.



지난 이틀의 컨퍼런스가 정말 많은 걸 배우고 자극이 되는 시간이었다.


당장 내년에는 또 어떤 컨퍼런스를 가볼까 


그리고 그 전까지 난 얼마나 더 발전할 수 있을 까 하는 생각이 든다.


'개발자세상' 카테고리의 다른 글

Kotlin  (0) 2018.10.30
Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Mobile세상 ....  (0) 2017.06.03
JavaScript polling  (0) 2017.03.17
BoneCP DB Pooling  (0) 2016.11.22
Posted by headiron
,

작년 부터 Device-Manager 프로젝트를 진행중이다.

회사에 들어오는 Traffic중 일정 Percentage의 Sample Traffic에서 UserAgent를 추출해서 

UserAgent 정보를 이용해서 OS/Browser/Device 정보를 추출하고 System에 없는 데이터는 추가하는 일이다.


프로젝트를 진행하면서 회사 내부 시스템도 좀더 깊게 알게 되고

Kafka consumer code, Angular, Redis, Scala 등도 실무로 적용해 보면서 

Technical하게 많은 도움이 된 ( 되고 있는 ) 프로젝트 이다.


Technical한 것과 별개로 Sample traffic data를 사용하면서 

Mobile Traffic이 상당히 큰 비중을 차지 하게 되는 걸 알게 되었다.


광고 회사다 보니 100% 정확하지는 않겠지만,

60% 넘는 Traffic이 Mobile Traffic ( Android 40%, iOS 20% )

Window 계열 Traffic이 30%, Mac OS가 4%정도 였다.


웹 관련해서는 그래도 좀 따라 갈 수 있다고 생각했는데 

Mobile Traffic이 PC Traffic을 이렇게 앞서고 있었구나 생각하니 나에겐 충격이고 또 아찔하게 다가왔다.


뭐 생각해보니 나도 잠깐 짬날때 움직이면서 폰으로 서핑도 하고 다니니 통계가 틀린 건 아닌 듯 싶다.


Back-end쪽 일을 많이 하고 있기는 하지만 Mobile 로 Trend가 넘어가고 있는 걸 내가 못 따라 가고 있다고 생각하니 걱정이 앞었다.


Machine Learning, Mobile, IoT 정말 많은 공부거리도 많고 내가 어디까지 Follow up할 수 있을 지 걱정이다.

뭐.. 그래도 해쳐나가야지 싶다.

 

'개발자세상' 카테고리의 다른 글

Apache 2.0, PHP 7.0 and Ubuntu  (0) 2017.12.20
Java 8 , Reactive  (0) 2017.07.16
JavaScript polling  (0) 2017.03.17
BoneCP DB Pooling  (0) 2016.11.22
Rotating Linux Log file  (0) 2016.03.10
Posted by headiron
,