블로그
전체 62021. 01. 21.
4
[리액티브 프로그래밍 에피소드] RxJava의 groupBy 연산자 추가 설명
안녕하세요? RxJava 강의를 진행하고 있는 Kevin입니다. 1부 강의를 수강하시던 수강생분의 질문 및 의견 사항이 있어서 다른 수강생분들에게 알리고자 블로그에 글을 남기게 되었습니다. 'Kevin의 알기 쉬운 RxJava 1부' 강의의 섹션 4 > 변환 연산자(2) 수업에서 groupBy를 설명하는 예제 코드가 있는데요. 그 중에서 두번째 예제 코드에 사용된 filter 연산자는 groupBy 연산자를 사용하면서 조금 쉬운 예를 보여드리려고 사용을 했지만 사실은 불필요하게 사용된 부분이 있습니다. 또한 groupBy 연산자의 진짜 사용 목적을 이해하기에 기존의 예제코드는 조금 부족한면이 있어서 groupBy 연산자 사용에 좀 더 적절한 예제 코드를 추가로 올려두었습니다. github에 올려둔 소스 코드를 잠깐 설명 드리자면, ==== ObservableGroupByExample03 === /** * 제조사를 그룹으로 묶어서 자동차 명을 출력하는 예제 */public class ObservableGroupByExample02 { public static void main(String[] args) { Observable, Car>> observable = Observable.fromIterable(SampleData.carList) .groupBy(Car::getCarMaker); observable .flatMapSingle(carGroup -> carGroup.flatMap(car -> Observable.just(car.getCarName())) .toList() ) .subscribe(System.out::println); }} : 제조사별로 자동차 명만 출력하는 예제입니다. groupBy( ) 연산자는 Observable을 반환을 하는데 이 GrouppedObservable을 flatMapSingle( ) 연산자를 이용해서 해당 그룹별로 통지되는 Car 객체 중에 CarName만 얻은 후,(CarName을 얻기 위해서 내부적으로 flatMap() 연산자를 한번 더 사용했음) toList()를 통해 Single로 CarName이 담긴 list를 통지하는데요. 여기서 flatMapSingle( ) 연산자는 Observable 이렇게 Observable이 이중으로 감싸져 있는 부분에서 바깥쪽 Observable을 한꺼풀 벗겨내고 GroupedObservable로 평탄화 시켜주는 역할을 합니다. flat이란 의미 자체가 평평하게 해준다는 그런의미가 있으니 이 의미를 기억하시면 될 것 같습니다. flatMap( )과 달리 flatMapSingle( ) 연산자는 새로운 Observable로 데이터를 여러번 emit 하는게 아니라 연산자 이름에서와 같이 Single Observable로 단 한번만 emit을 한다는 사실 역시 기억을 해두시구요. flatMapSingle( ) 연산자 내부에 있는 flatMap( ) 연산자는 Observable에서 바깥쪽에 감싸져 있는 Observable을 벗겨내고 Car 객체로 평탄화 시켜주며, 이를 통해서 Car Name을 얻을 수 있고, toList( ) 연산자를 사용해서 Single로 한번만 emit 되게 됩니다. 출력 결과는 아래와 같습니다. ===================================== [티볼리, G4렉스턴] [SM6, SM5] [말리부, 트래버스, 트랙스] [쏘렌토, 팰리세이드] 그리고 네번째 예제 코드를 하나 더 추가했습니다. ==== ObservableGroupByExample04 ==== /** * 제조사 별로 그룹으로 묶은 후, 제조사 별 차량 가격의 합계를 구하는 예제 */public class ObservableGroupByExample03 { public static void main(String[] args) { Observable, Car>> observable = Observable.fromIterable(SampleData.carList) .groupBy(car -> car.getCarMaker()); observable .flatMapSingle(carGroup -> Single.just(carGroup.getKey()) .zipWith( carGroup.flatMap(car -> Observable.just(car.getCarPrice())) .reduce((p1, p2)-> p1 + p2) .toSingle() , (key, sum) -> key + ": " + sum ) ) .subscribe(System.out::println); }} : 제조사 별 차량 가격의 합계를 구하는 예제인데요. 위의 ObservableGroupByExample03 코드와 거의 같은데 다른점은 제조사 별 차량 가격의 합계를 구하기 위해 reduce( ) 연산자를 한번 더 사용했다는 건데요. 조금 복잡해 보이지만 flatMapSingle( ) 내부를 잠깐 설명 드리자면, 차량 가격 합계 앞에 제조사를 표시해주기 위해서 zipWith( ) 연산자를 추가적으로 사용을했는데 .zipWith( ) 연산자는 zipWith( )연산자를 호출한 Observable source와 zipWith( ) 의 파라미터로 입력된 Observable source를 결합시켜서 가공된 데이터를 반환하는 연산자인데요. 위 코드에서 보시면, flatMapSingle( ) 내부의 Single.just(carGroup.getKey())의 Single과 zipWith( ) 의 파라미터로 입력된 Single(마지막에 toSingle( )이 붙어서 Single로 변환 됨)을 결합해서 새로운 데이터, 여기서는 key + ": " + sum 을 반환합니다. reduce( ) 연산자는 파라미터로 입력된 데이터 두개씩 누적하여 더해서 최종 결과로 하나의 데이터만 반환하기 때문에 Observable.just(1개 데이터)로 호출할 수 있고, 이를 다시 toSingle( ) 연산자를 사용해서 Single 로 변환될 수 있는것입니다. 출력 결과는 아래와 같습니다. ================================ CHEVROLET: 91000000 HYUNDAE: 61000000 SSANGYOUNG: 66000000 SAMSUNG: 75000000 좋은 지적을 해주신 윤지상님께 감사드리고, 다른 의견 있으시면 언제든지 문의 주세요. 감사합니다.
2021. 01. 21.
4
[리액티브 프로그래밍 에피소드] Hello Reactor 들여다 보기
안녕하세요? [Kevin의 알기 쉬운 RxJava] 강의를 진행하고 있는 Kevin입니다. 이번 시간에는 'Hello, Reactor' 코드를 가지고 Reactor의 기본 구조를 들여다보는 시간을 가져보겠습니다. 개발에 처음 입문하실때 대부분 'Hello World!' 코드를 실행해보셨을텐데요. Reactor 역시 마찬가지로 'Hello, Reactor' 메시지를 출력해보면서 Reactor의 기본 구조를 간단하게 살펴보도록 하겠습니다. 어렵지 않으니 가벼운 마음으로 글을 읽어주시면 감사드리겠습니다.^^ 먼저 아래의 코드를 보시죠. [Hello Reactor 코드] 여러분들이 아시다 시피 Reactor는 RxJava와 마찬가지로 Reactive Streams라는 표준 사양을 구현한 구현체입니다. 따라서 Reactive Streams에서 정의하고 있는 생산자 즉, Publisher와 소비자 즉, Subscriber를 구현하고 있는데요. 위의 코드에서 보시는것처럼 Reactor에서는 Flux가 대표적인 생산자 중에 하나입니다.위의 코드에서 소비자라고 되어 있는 부분은 람다 베이스 Subscriber가 되겠습니다. 생산자 쪽에서는 just라는 Operator(연산자)를 사용해서 두 개의 데이터를 소비자 쪽으로 통지를 하는데요. Reactor에서는 생산자 쪽에서 통지할 데이터를 정의하는 과정 자체를 묶어서 'Sequence(시퀀스)'라고 합니다. 이 Sequence라는 용어는 Reactor를 접하다보면 자주 나오는 용어이니 기억을 해두시길 바래볼게요. 생산자 쪽에서 소비자 쪽으로 데이터를 통지하는것이 맞긴하지만 최종 소비자까지 데이터가 전달 되기까지는 중간에 여러 Operator를 만날 수 있기때문에 엄밀히 말하자면 생산자가 소비자에게 데이터를 통지한다라고 말하기보다는 생산자가 Downstream으로 데이터를 내보낸다라는 표현이 더 정확할 것 같네요. 용어에 대한 부분은 아래쪽에서 다시 정의를 해보도록 하구요. 아무튼 생산자 쪽에서 데이터를 통지하게 되면 최종 소비자 쪽에 바로 데이터가 전달되는 것이 아니라 map( )이라는 Operator에서 원본 데이터가 가공 처리 된 후에 최종 소비자 쪽으로 전달이 되는것을 볼 수 있는데요. 여기서는 통지된 String 데이터를 소문자로 변환을 한 후에 최종 소비자쪽으로 전달하고 있네요. 자, RxJava 강의 시간에도 말씀을 드렸지만 리액티브 프로그래밍은 크게 세가지의 step으로 이루어져있습니다. 1 step : 생산자가 데이터를 통지한다.2 step : 통지된 데이터를 Operator로 가공한다.3 step : 가공 처리된 데이터를 최종 소비자에게 전달한다. 이 세가지 큰 흐름은 기본적으로 꼭 기억을 해두시고, 나머지는 데이터를 통지하는 다양한 방법, 데이터를 가공하는 다양한 방법, 비동기 프로그래밍을 위한 쓰레드를 할당하는 방법, 에러 처리 방법 등을 단계적으로 적용 하는 식으로 학습을 진행해 나가면 리액티브 프로그래밍을 조금 더 수월하게 이해하실 수 있을거라는 생각이 드네요. ^^; 자, 그럼 마지막으로 Reactor에 대한 에피소드를 계속 진행가기 전에 Reactor에서 사용되는 여러가지 용어를 정의하고 에피소드를 마무리 하도록 하겠습니다. 먼저 아래 용어들을 보시죠. Publisher : 발행자, 게시자, 생산자, 방출자(Emitter) Subscriber : 구독자, 소비자 Emit : Publisher가 데이터를 내보내는 것(방출하다. 내보내다. 통지하다.) Sequence : Publisher가 emit하는 데이터의 연속적인 흐름. 스트림과 같은 의미라고 보면 됨 Subscribe : Subscriber가 Sequence를 구독하는 것 Dispose : Suscriber가 Sequence 구독을 해지 하는 것 Downstream : 현재 Operator 체인의 위치에서 봤을때 데이터가 전달 되는 하위 Operator 및 method 체인 Upstream : 현재 Operator 체인의 위치에서 봤을때 상위 Operator 및 method 체인 여태껏 제가 데이터를 통지하는 쪽은 생산자로 지칭했는데요. 보시는대로 생산자 이외에 발행자, 게시자, 방출자 등 다양하게 사용이 되고 있습니다. 모두 같은 의미라고 보시면 되겠지만 앞으로 에피소드를 진행할 때는 그냥 영어로 Publisher라고 지칭하도록 하겠습니다. ^^; 따라서 소비자 역시 영어로 Subscriber라고 지칭하면 되겠구요. 데이터를 통지하는 행위 역시 영어 그대로 Emit 한다라고 하겠습니다. Sequence는 위에서 잠깐 말씀 드렸죠? Publisher쪽에서 데이터를 emit하는 흐름 자체를 통칭하는 것을 의미하는데, 예를 들어서 Flux라는 Publisher가 데이터의 Emit을 정의하는 부분을 설명할때 Sequence를 생성한다 라고 표현할 수 있겠습니다. Subscribe와 Dispose는 구독하다, 구독을 해지하다라고 표현하도록 하겠습니다. 마지막으로 Downstream과 Upstream이라는 용어인데요. Reactor를 학습하다보면 종종 나오는 용어인데 개념적으로 이해하기 모호한 면이 있는 용어중에 하나이기도 합니다. 이럴때는 그냥 단순하게 이해를 하는게 제일 좋을거라고 생각을 해보게되네요. ^^;예를 들어 위의 코드에서 just( )의 위치에서 Downstream은 map( )부터 subscribe( )까지 하위 체인이 되겠습니다. 그리고 subscribe( ) 입장에서는 map( )과 just( )가 Upstream이 되겠구요. just( )의 내부를 들여다보면 return 값으로 Flux를 반환하는데요. just( )에서 반환하는 Flux를 원본 Flux가 되겠습니다. 그리고 map( )에서 반환하는 return 값 역시 Flux인데요. 여기서의 Flux는 원본 Flux가 아닌 가공 처리된 데이터를 가지고 있는 새로운 Flux입니다. Flux(또는 Mono)의 이러한 처리 흐름때문에 Downstream이나 Upstream이라는 용어가 생겨난것 같은데 위에서 언급드린것처럼 단순하게 생각해주시면 될것 같아요. 자, 오늘은 'Hello, Reactor' 코드를 통해서 Reactor 의 기본 구조를 살펴보았는데요. 다음 시간에 다른 에피소드를 가지고 다시 찾아뵙도록 하겠습니다. ^^ 감사합니다!
2021. 01. 21.
5
[리액티브 프로그래밍 에피소드] 이벤트 루프란?
수강생 여러분 안녕하세요. RxJava 강의를 진행하고있는 Kevin입니다. 오늘은 리액티브 프로그래밍과 밀접한 관련이 있는 이벤트 루프에대해서 잠시 알아보도록하겠습니다. 이벤트 루프에 대해서 먼저 이야기 하기 전에 저희는 서블릿에 대한 언급을 먼저 하고 넘어가야되는데, 그 이유는 이벤트 루프라는 개념이 나오게 된 배경에는 서블릿이 있기때문이에요. 그럼 서블릿에 대한 이야기를 먼저 해볼까요? 서블릿의 기본 개념 서블릿은 뭘까요? 자바를 사용하는 개발자이거나 자바를 배우고 계신 분들이 웹 애플리케이션을 만들어 보셨다면 이미 서블릿을 사용해보셨을겁니다. 여러분들이 JSP를 사용해보셨거나 아니면 Spring framework을 사용해보셨다면 여러분들은 알게 모르게 서블릿이란 놈을 사용해보셨다는 말씀. ^^ 서블릿은 웹에서 클라이언트의 요청을 동적으로 처리하기 위해 서블릿 규약이라는 일정한 규칙에 맞춰서 작성되는 클래스인데요. 이 클래스들이 클라이언트로 부터 들어오는 요청을 받아서 응답으로 되돌려주는 역할을 하죠. 개발자가 작성한 서블릿 클래스가 HttpServlet을 상속 받고, doGet( ), doPost()를 구현하는 것이 서블릿 클래스의 기본이라는 사실은 서블릿 클래스를 사용해보신분들은 너무나 잘 알고들 계실겁니다. Spring에서의 서블릿 어쨌든 저희가 HttpServlet 같은 상위 클래스를 상속 받아서 개발을 진행할건 아니기때문에 서블릿에 대해서 더 자세한 이야기를 할 필요는 없을 것을 같네요. 다만, 이것 하나만은 기억을 하셔야 될 것 같습니다. Spring MVC 역시 내부적으로는 Servlet 기술을 사용을 한다는것을요. DispatcherServlet 이라는 녀석을 기억하시죠? Spring MVC에서는 이 DispatchServlet이라는 녀석이 최앞단에서 클라이언트의 요청을 전달 받아서 해당 요청에 매핑되는 Controller 에게 요청을 전달한다는 사실은 Spring MVC로 개발을 해보신분들은 잘 알고 계실겁니다. 서블릿 방식의 문제점 그런데 이러한 서블릿을 사용하여 클라이언트의 요청을 처리하는 방식에는 큰 문제점이 하나 있는데요. 서블릿 방식은 클라이언트에서 요청이 들어오면 해당 요청을 처리하기 위해서 요청 당 쓰레드 하나씩을 생성해서 처리합니다. 하나의 쓰레드에서 클라이언트의 요청을 다 처리하면 이 쓰레드는 쓰레드풀이라는 쓰레드의 저장소에 다시 반납이 되는데, 참고로 이 쓰레드 풀은 톰캣 같은 서블릿 컨테이너가 관리를 해줍니다. 사실 클라이언트의 요청이 폭주만 하지 않으면 지금과 같은 서블릿 방식이 큰 문제가 되지는 않겠지만 클라이언트의 요청이 쓰레드의 갯수에 비해 기하급수적으로 늘어나는 순간 문제가 시작됩니다. 요청을 처리하기 위한 쓰레드가 쓰레드 풀에 남아있지 않을 경우 기존에 사용되던 쓰레드가 쓰레드 풀에 다시 반납이 되어 다른 요청을 처리하기 위해서 재사용할 수 있 때까지 클라이언트로 부터 들어온 요청들은 대기를 해야되니까요. 이런 성능상의 문제점을 상당 부분 해소할 수 있는 방식이 바로 이벤트 루프 방식인데요. 그럼 이벤트 루프 방식이 무엇인지, 어떻게 클라이언트의 요청을 효과적으로 처리하는지 간단하게 살펴볼까요? 이벤트 루프란 아래 그림을 보면서 이벤트 루프에 대해서 설명 드리겠습니다. 클라이언트가 서버로 요청을 보내면 요청 핸들러가 클라이언트의 요청이 들어왔다는 이벤트를 이벤트 루프에 푸시합니다. 이벤트 루프는 그림과 같이 계속해서 루프를 돌면서(한마디로 무한루프) 요청 핸들러로부터 푸시된 이벤트를 감지합니다. 그리고 나서 해당 이벤트에 대한 콜백을 등록한 후, 클라이언트가 요청한 작업을 처리합니다. 작업이 끝나면 작업이 끝났다는 이벤트를 이벤트 루프에 푸시하고 등록된 콜백을 호출한 후, 요청 핸들러를 다시 거쳐서 클라이언트에게 최종적으로 응답을 되돌려줍니다. 어떠신가요? 이벤트 루프가 무엇인지 대충 감이 오시는지 모르겠네요. 이벤트 루프 방식의 장점은 쓰레드 하나로 굉장히 많은 요청을 병렬로 처리하기때문에 기존의 서블릿 방식의 성능상의 문제를 해결한다는것입니다. WebFlux와 이벤트 루프 Spring WebFlux가 바로 이벤트 루프 방식을 사용하기때문에 대량의 클라이언트 요청을 효과적으로 처리할 수 가 있게되었는데요. Spring WebFlux를 사용해서 대량의 클라이언트 요청을 효과적으로 처리하는 애플리케이션을 한번 만들어보고 싶어지지 않으셨나요? ^^; Spring MVC냐 Spring WebFlux냐 자, 그러면 무조건적으로 Spring MVC 대신에 Spring WebFlux를 사용하면 좋은것이냐하면 사실 그건 아닌것같습니다. Spring MVC로 개발을 진행해보셨다면 아시겠지만 생산성이 대단하다는것을 느끼실 수가 있을겁니다. 그리고 RxJava 2부 강의에서 비동기 방식의 디버깅에 대한 이야기를 드리겠지만 비동기 방식보다는 동기 방식이 디버깅도 용이하고 여태껏 사용해온 익숙한 명령형 프로그래밍 방식으로 코드를 짜면 되니 코드를 짜는 부담 역시 줄어드는게 사실일테구요. 하지만 분명한것은 사물 인터넷, 자동차, 인공 지능 등등 우리가 생각하는 전통적인 클라이언트 이외에 다양한 클라이언트들이 계속해서 생겨날텐데 이런 종류의 클라이언트들이 계속해서 생겨나면 생겨날수록 서버가 감당해야 되는 요청의 수는 점점 늘어나겠죠. 마이크로 서비스로 인해서 또한 서비스들 간의 요청도 점점 늘어나고 있기도 하구요. 결론은 지금 당장은 아니더라도 개발자로서 미래를 준비하고 싶으신 분은 리액티브 프로그래밍 기법을 꼭 익혀두셨으면 하는 바램입니다. ^^ 이야기는 길었는데 결론은 꽤 간단하다는.. ^^;; 오늘은 이벤트 루프에 대한 이야기를 간단하게 해보았는데요. Spring WebFlux에 대한 이야기로 또 찾아뵙도록 할게요. 감사합니다~
2021. 01. 21.
8
[리액티브 프로그래밍 에피소드] 리액터와 WebFlux
RxJava 강의를 수강하시는 수강생 여러분 안녕하세요? 강의를 진행하고 있는 Kevin이라고 합니다. 지난번 공지에서 잠깐 말씀을 드렸다시피 매주 한두번 정도 시간을 내서 강의에서 제대로 얘기하지 못했던 리액티브 프로그래밍에 대한 뒷 얘기들을 조금씩 해볼까 합니다. 리액티브 프로그래밍을 배우고자 하시는 분들께 조금이나마 더 도움이 되길 바래보겠습니다. 리액터(Reactor)란 무엇일까요? 리액티브 프로그래밍에 대해서 처음 들으시는 분들은 리액터에 대해서 당연히 모르실거 같은데 아마도 스프링을 학습하면서 들어 보신분도 있지 않을까하는 생각도 들긴하네요. ^^ 예상하신분도 계시겠지만 리액터는 Java로 구현 된 리액티브 프로그래밍의 한 종류입니다. 더 정확히 얘길 하자면 Reactive Streams를 구현한 구현체라고 볼 수 있는데요. 강의를 수강하신 분들은 이미 알고 계시지만 RxJava 역시 Reactive Streams를 구현한 구현체의 하나라고 볼 수 있습니다. 일반적으로 Reactive Streams를 구현한 구현체들은 대부분 Rx~로 시작을 하는데 Reactor는 그것보다 더 확실하게 "나는 리액티브 프로그래밍을 사랑하는 Reactor야" 라고 얘길 하는것 같군요.^^ Reactor라는 이름에서 리액티브 프로그래밍의 느낌이 팍팍 오지 않으신가요?ㅎ 리액터(Reactor)를 배워야 할까 말아야 할까 결론부터 말씀드리자면 리액티브 프로그래밍을 배우기로 하셨다면 리액터는 배우는것이 맞다고 생각합니다. 두가지 이유만 얘길 드리자면 먼저 리액터를 통해서 저희는 명령형 프로그래밍의 한계를 넘어설 수 있는 그리고 시대에 맞는 개발 패러다임을 이해하고 실무에 점차적으로 사용을 하게 될 것입니다. 끊임없이 생산되는 데이터를 효과적인 비동기 상태로 처리할 수 있어야 한다는 사실은 필연적이라는 생각이 드니까요. 그렇기 때문에 Reactor는 꼭 학습을 하시는게 좋을 것이라는 생각이 드네요. 굳이 왜 리액터일까? 근데 왜 굳이 리액터를 배워야 되는가.. 라고 생각을 하실수도 있겠네요.^^; 저희는 지금 RxJava를 배우고 있는데 말이죠. 음.. Java 애플리케이션을 개발해보신 분들은 아시겠지만 Java 애플리케이션을 개발하면서 Spring Framework을 빼놓고 얘기하는게 어려워진 것은 오래되었습니다. 물론 Spring을 사용하지 않고, 애플리케이션을 만들 수는 있지만 Spring을 일단 한 번 사용하게되면 Spring 없이 개발하겠다고 얘기하는 분들은 많지 않을거 같아요. Spring 얘기를 왜 하느냐하면 Reactor가 바로 Spring5에서 지원하는 Reactive 프로그래밍의 기본이 되기 때문인데요. Spring을 사용하시는 분들, 그리고 앞으로 Spring을 접하실 분들이라면 Spring과 궁합이 딱 맞는 Reactor를 배우지 않을 이유가 있을까 싶습니다. Spring과 Reactor를 사용해서 Spring MVC 기반의 애플리케이션 대신에 리액티브 애플리케이션을 만들어보는것. 재미있을 것 같지 않나요? ^^ 그럼 RxJava는 배우지 말라는거? 그건 당연히 아닙니다. 제가 RxJava 강의를 오픈한 가장 큰 이유 중에 한 가지는 RxJava라는 기술 자체 보다는 리액티브 프로그래밍에 대해서 알려드리고 싶어서이기 때문인데요. 리액티브 프로그래밍은 처음 접하게 되면 이해하기가 쉽지 않기때문에 리액티브 프로그래밍에 대한 기본 개념을 잡을 수 있도록 하는것이 제 강의의 가장 큰 목표라고 볼 수 있습니다. 그런 의미에서 제 강의는 다른 의미로 여러분들한테 충분히 의미있는 강의가 될거라고 믿어보겠습니다.^^ 제 강의를 듣고 Reactor를 접하게 된 후에 생각했던 것보다 Reactor가 어렵지 않구나라는 얘기를 꼭 들었으면 좋겠네요. ^^ Reactor는 이제 알겠는데 WebFlux는 뭐지? 저희 강의를 조금이라도 수강을 하신 분들은 알고 계실텐데요. RxJava에서 데이터를 통지(또는 발행, 방출)하는 생산자의 역할을 하는 놈이 Observable, Flowable, Single, Maybe 등인데, Reactor에서 이러한 역할을 하는 놈이 바로 Flux와 Mono라는 놈입니다. RxJava에서는 데이터를 한 건만 통지할 때에는 Single을 사용하고, 데이터를 한 건도 통지하지 않거나 한 건만 통지할 때는 Maybe를 사용 하죠. 그리고 데이터를 한 건 이상 통지할 때에는 Observable 또는 Flowable을 사용을 합니다. 뭔가 좀 복잡하죠? Reactor에서는 이걸 조금 단순화해서 Mono라는 놈은 딱 한 건의 데이터만 처리하고, Flux는 한건도 통지하지않거나 한건 이상 통지하는데 사용을 하도록했습니다. Flux에 대해서 말씀을 드렸으니 WebFlux는 무얼하는 놈인지 대충 감이 오시죠?'혹시 Web에서 사용하는 Flux?' 맞습니다.^^ Spring MVC가 웹 계층에 특화된 웹프레임워크인 것과 마찬가지로 WebFlux는 웹 계층에서 비동기 처리를 하는데 특화된 리액티브 프로그래밍 기반의 웹 프레임워크라고 할 수 있습니다. 그러니까 우리는 WebFlux라는 저놈을 Spring MVC 처럼 효과적으로 잘 사용 하기 위해서 Reactor를 먼저 배우게 되는 것입니다. 구체적으로 어떻게 사용하는지는 아직 자세히 모르더라도 WebFlux가 대충 뭐하는 놈인지는 대충 이해가 되시죠? 그러면 Reactor의 Flux를 사용하는 코드 예시를 조금 살펴보고 오늘 이야기를 마무리 하도록할게요. 먼저 RxJava에서 사용하는 코드부터 간단하게 살펴보겠습니다. @Testpublic void ObservableFilterTest() { Observable observable = Observable .just(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) .filter(n -> n % 2 == 0); observable.test() .assertValues(2, 4, 6, 8, 10) .assertComplete();} RxJava 2부 강의에서 만나보시겠지만 Observable에서 통지하는 데이터들에 대한 Unit Test 코드입니다. Observable의 just() 함수를 사용해서 1부터 10까지 10개의 데이터를 통지하면 filter() 함수에서 통지된 데이터를 2로 나눈 나머지가 0인 숫자 즉, 짝수인 숫자만 필터링을 해서 최종적으로 소비자 쪽에 통지를 하는 간단한 코드인데요. 이렇게 통지된 데이터가 정상적으로 소비자 쪽에 전달이 되는지 검증하기 위해서 Observable의 test() 함수를 이용해서 검증을 합니다. 자, 그러면 이번에는 Reactor에서 사용하는 코드를 한번 보실까요? @Testpublic void fluxFilterTest() { Flux flux = Flux .just(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) .filter(n -> n % 2 == 0); StepVerifier.create(flux) .expectNext(2, 4, 6, 8, 10) .verifyComplete();} Flux의 just()함수를 사용해서 1부터 10까지 10개의 데이터를 통지하면 filter()함수에서 역시 짝수인 숫자만 필터링을 해서 소비자 쪽에 통지를 합니다. 그러면 StepVerifier 클래스를 이용해서 소비자 쪽에 전달되는 데이터를 검증을 하고 있습니다. RxJava와 거의 똑같다는거 느껴지시죠? 그렇기때문에 여러분들은 저희 강의를 통해서 리액티브 프로그래밍의 기본 개념을 확실하게 자기 것으로 만든 후에 Reactor의 코드를 보면 '아.. 어렵지 않네?'라고 말씀하실수 있을거라고 생각합니다. ^^ 그럼 저는 다음 시간에 리액티브 프로그래밍의 또 다른 에피소드를 가지고 다시 뵙도록 할게요. 감사합니다!
2021. 01. 21.
5
비전공자가 개발자로 입문하고 성장하기 위한 방법 조언
안녕하세요, Kevin입니다. 새벽에 아기가 깨서 다시 재웠는데 잠이 안와서 이렇게 몇자 적게되었네요. 인프런에 Java 개발자 로드맵을 오픈한지 1년 6개월이 넘은거 같은데 매일 매일 지속적으로 수강 신청을 해주시는거 보면서 개발자가 되고자 하시는분들이 참 많구나 라는걸 새삼 느끼게 되는데요. 한편으로는 개발자 되는 길이 너무 막막해서 어디서부터 시작해야될지 몰라서 헤매었던 과거의 제 모습이 문득 생각이 나더라구요. 처음 접하는 용어와 프로그래밍 문법들이 많이 어려웠었고, 전체적인 개념을 잡는게 너무 어려웠던게 사실이니까요. 아무튼 지난 일들을 생각해보면 저 역시도 개발자가 되기 위해서 순탄한 길을 걷지 못했구나 라는 그런 생각이 듭니다.ㅎ 아무튼 개발자로서 입문 하기 위한 현실적인 방법에 대해서 잘 나와 있는 글들이 있어서 새벽에 잠깐 소개 드릴게요. - 소프트웨어 개발자가 되기 어려운 이유: https://www.techm.kr/news/articleView.html?idxno=2137- 개발 배우기가 정말 어려운 이유: https://brunch.co.kr/@jypthemiracle/14 글들을 보시면 아시겠지만 비전공자가 개발자로 입문하는것은 정말 쉬운일이 아니라는 생각이 드네요. 저처럼말이죠. 하지만 절대 넘을 수 없는 벽도 아니고, 일단 입문을 하게되면 해볼만하단 것과 실제로 너무 재미있다는 얘기 또한 드리고싶습니다. 그러니 이왕 시작하기로 마음 먹으셨다면 절대 포기하지 마시고, 열심히 노력하셔서 꼭 원하시는 개발자의 세계로 입문 하실 수 있길 멀리서나마 기원 드려봅니다. 질문이 있으시면 언제든지 성심 성의껏 답변 드릴테니까 편하게 해주시면 감사드리겠습니다. 그럼 저는 또 시간내어 찾아뵐게요. 감사합니다.
2021. 01. 20.
10
자신에게 맞는 회사 찾기(for Java Developer)
수강생 여러분 안녕하세요? 코로나 확산으로 인해서 생활하시는데 어려움이 많으시죠? 다들 건강하게 목표로 하시는 일들 잘 이루시길 바래 보겠습니다. 오늘은 개발자로서 처음 사회에 발을 디디시는 분, 그리고 개발 경력이 아직은 짧은 분들에게 입사 또는 이직을 위해 어떤 기업을 선택하는것이 좋을지 제가 경험한 내용을 토대로 얘기를 드려볼까해요. 각자의 생각과 의견이 모두 다른만큼 제가 말씀드리는 이야기는 기업을 선택하시는데 있어서 참고만 할 수 있는 용도가 되길 바래보겠습니다. 저희 강의가 자바 개발자 로드맵이니 자바 개발자 위주로 얘길 드리겠습니다. 자바 개발자가 되는 것은 과연 괜찮은 선택일까? 저희 나라에는 현실적으로 자바 개발자의 수요는 많은 편입니다. 많은 기업들이 백엔드의 서버 애플리케이션으로 자바 기반의 애플리케이션을 사용하고 있기때문에 자바 개발자의 수요는 여전히 적은편은 아니라고 생각합니다. 안드로이드 앱 개발은 두말 할 나위도 없을테구요. 자바를 먼저 배울까 파이썬을 먼저 배울까 그리고, 요즘 처음 개발에 입문하시는 분들은 배우기 쉽고, 직관적인 파이썬으로 많이들 입문하시는데 제가 처음 개발에 입문할 때와 마찬가지로 현재까지도 개발 입문 언어로 자바를 많이들 선택을 하는걸로 알고 있습니다. 어떤 언어를 선택하느냐는 전적으로 개인의 선택이겠지만 시장의 수요를 잘 고려하셔서 선택을 하셔야 될 것 같은데, 파이썬의 Django나 Flask 등을 사용해서 웹 애플리케이션 개발을 하기도하지만 최근에는 데이터 과학(인공지능 개발 포함) 분야에서 파이썬이 인기를 끌고 있는게 사실입니다. 저도 데이터 과학 쪽에 관심이 많고, 미래를 준비하기위해서 시간을 쪼개서 파이썬을 학습하고 있는 중이기도합니다. 처음부터 데이터 과학 분야의 길로 가시고 싶다면 자바보다는 파이썬을 먼저 배우는게 당연히 낫겠죠? 그리고 처음 프로그래밍에 입문 할 때 역시 배우기 쉬운 파이썬이 적합하다라고 합니다. 하지만 채용 시장의 수요를 생각하면 자바는 필수이지 않을까라고 생각해보게되네요. 강의에서도 말씀 드렸지만 자바 개발자가 되기 위해서는 어떤 것들을 알아야되고 배워야 하는지에 대한 구체적인 내용은 나중에 다시 얘기를 드리겠구요. 오늘은 순전히 자바 개발자로서 자신에게 맞는 기업을 잘 선택하기 위한 기준과 기업 유형에 대해서 주로 얘기를 해볼까 합니다. 내 성향에 맞는 기업은 어떤 기업일까? 그럼 자신에게 맞는 기업이라는 것의 기준은 무얼까요? 우선 첫번째로 자신의 성향을 스스로 잘 파악하고 있어야 될 것 같습니다. 최근에는 기업의 조직문화가 과거의 수직 구조에서 수평적인 구조로 바뀌는 경우가 점점 많아 지고 있는데요. 개인적인 생각으로는 우리 나라 기업의 수직 구조는 군대 문화가 많은 영향을 끼친것 같다는 생각이 듭니다. ㅡ.ㅡ 아무튼 그런 딱딱한 수직 구조에서 부드러운 수평 구조로 바뀌어 가고 있는 추세인건 틀림없다라는 생각이 들긴하는데, 특히나 그런 경향은 스타트업 기업의 경우에 더 두드러지는것 같습니다. 수평 문화의 대표적인 특징은? 수평 문화가 자리 잡은 기업에는 직급이라는게 없는 기업이 많고, 누구누구 님~ 이렇게 부르면서 직급을 신경쓰지 않고 동료 간에 자유롭게 자기 의견을 주고 받는 경우가 많습니다. 어떤 기업들은 한국 이름 대신에 영어 이름을 사용해서 조금 더 수평적인 관계를 유지하려고도 하구요. 나는 수직? 아니면 수평적인 성향? 자, 그러면 여기서 자신이 수직적인 문화가 잘 맞는지 수평적인 문화가 잘 맞는지 곰곰이 한번 생각을 해보는것도 자신에게 맞는 기업을 선택하는 방법중에 하나라고 볼 수 있겠습니다. ^^; 예를 들면, 저 역시도 수평적인 문화가 단점보다는 장점이 더 많다라고 생각은하지만 수평적 문화에 낯설어하시는 분들도 꽤 있으신거 같더라구요. 수평적인 문화가 정착이 된 기업 같은 경우에는 멤버들간에 직급이나 나이에 크게 신경을 쓰지 않고, 오직 서로가 팀에 속한 팀원이라고 생각하고 업무를 진행하는 경우가 대부분이니 그런 조직 문화가 어색하거나 어색해서 개선을 해야되는데 도저히 개선이 되지 않는다면 수평적인 문화가 본인한테 맞지 않을 가능성이 높을거라고 생각합니다. 나에게 맞는 기업 유형은? 다음으로 자신이 어떤 업무 타입의 기업에서 일을 하고 싶은지에 대해서 고민을 해볼 필요가 있습니다. 자바 개발자로서 일을 할 수 있는 기업의 유형은 크게 시스템 통합, 웹 에이전시, 자체 소프트웨어 또는 서비스 제공 기업으로 나눌 수 있을 것 같습니다. 시스템 통합 기업의 특징 시스템 통합은 System Integration, 흔히들 말하는 SI 기업입니다. SI 기업은 주로 고객(금융권, 공공 기업, 학교 등의 단체)의 의뢰를 통해 해당 고객의 요구사항에 맞춰서 고객이 요구하는 시스템을 만들어 주는데요. 저희 나라에서는 시스템 통합을 위한 개발을 고객사에 직접 파견을 나가서 수행을 하게 되는 경우가 많습니다. 작게는 10명 미만 많게는 수백명으로 구성된 프로젝트 매니저, 설계자, 개발자들이 짧게는 수개월 길게는 1년 이상의 프로젝트 기간동안 함께 시스템을 구축 합니다. 요즘은 어떤지 모르겠지만 일단 대체적으로 야근이 많은 편입니다. 야근이 많은 이유는 여러가지 복합적인 이유가 존재하겠지만 SI 프로젝트 자체가 고객의 요구사항을 직접적으로 반영해야되는 구조이고, 기간내에 프로젝트를 끝내지 못하면 지체 상환금을 지불해야되는 구조도 많다보니 일단 프로젝트 기간이 정해지면 그 기간안에 끝내기 위해서 야근을 많이 하는 그런 구조인 경우가 많은것 같은데 아마도 모든 SI 기업이 그렇지는 않을거라고 생각하지만 아무튼 그러한 경향이 많다는 사실은 여러분들도 알고 계셔야할것 같네요. 웹 에이전시 다음으로 웹 에이전시가 있는데요. 웹 에이전시는 과거에는 주로 기업, 공공기관 등의 웹 사이트를 제작하는 비중이 높았었는데 최근에는 웹 에이전시 기업에서도 시스템 통합처럼 규모가 있는 프로젝트를 진행하는 경우도 많은데요. 제가 웹 에이전시에서 근무한적은 없지만 친한 지인이 웹 에이전시에서 근무하면서 규모있는 프로젝트를 진행하는것을 보았더랬습니다. 웹에이전시에서는 과거에는 PHP를 상당히 많이 사용했었는데 요즘은 어떤지 모르겠네요. JSP를 아직도 사용하고 있는 기업도 더러 있는것 같던데 제대로 된 애플리케이션을 개발하기 위해서는 JSP 기술 자체만을 사용하는 것은 지양되고 있다는 사실을 기억해두시면 좋겠습니다. 참고로 고객에 대한 컨설팅 업무도 SI 기업이나 웹 에이전시 기업에서 병행한다는 사실도 추가로 말씀드릴 수 있겠네요. 자체 소프웨어 또는 서비스 제공 기업 세번째로 얘기 드릴 수 있는 기업은 자체 소프트웨어나 서비스를 제공하는 기업을 들 수 있겠는데요. 자체 소프트웨어를 판매하는 대표적인 기업 유형은 보안을 전문으로 하는 기업을 들 수 있겠습니다. IT 보안 전문회사에서는 주로 바이러스 백신, DRM 솔루션, 암호화 솔루션, 웹 방화벽 등의 제품을 기업이나 공공기관에 납품을 하고 관리를 해주게되는데요. 온라인 서비스를 제공하는 경우도 있겠지만 고객사에 방문해서 고객 시스템에 자사의 보안 솔루션을 설치하고 구성을 해주는 경우가 많습니다. 그렇기때문에 보안 회사의 경우에는 보안 솔루션 자체를 깊게 연구하고 개발하는 연구원들이 따로 있고, 실제로 고객사에 자사의 보안 솔루션을 설치, 구성, 설치 후 지원을 해주는 기술 지원팀이 추가로 구성이 되어 있는 경우가 많은데요. 개발자들을 고객사에 파견해서 프로젝트를 진행하는 SI 기업과는 약간 성격이 다르지만 종종 기술 지원이 끝날때까지 고객사에 짧은 기간 동안 상주를 하는 경우도 있다는 사실을 기억해두시면 좋을 것 같네요. 설치형 소프트웨어가 아닌 서비스를 제공해주는 기업들도 많죠? 기업 이름을 일일이 열거하기가 좀 그렇지만 여러분들도 많이들 알고 계시는 대형 게임 회사들, 포털 사이트, 온라인 전자 상거래 기업 등의 서비스 제공 기업은 상당히 많은게 사실입니다. 이러한 서비스 제공 기업들은 대부분의 서비스를 온라인으로 제공을 하기 때문에 파견 근무가 거의 없다고 볼 수 있구요. 이런 서비스 제공 기업들은 더 좋은 서비스를 만들기위한 고민을 많이 하기때문에 기술 트렌드에 관심을 가지는 기업들이 많습니다. 물론 기술 트렌드만 쫓아간다고해서 좋은 서비스를 제공하는건 아니지만 발전하는 기술을 분석하고 자사의 서비스를 더 좋은 서비스로 개선하기 위한 노력들을 끊임없이 하는것이라고 보시면 될것같네요. 여러분들은 어떤 유형의 기업에서 일하고 싶으신가요? 자, 오늘은 세가지 정도 유형의 기업들에 대한 얘기를 해보았는데요. 어떠신가요? 여러분들에게 맞는 유형의 기업은 어떤 기업일까요? 저는 다른건 제쳐두고 제가 지금보다 더 성장할 수 있고, 더 발전할 수 있을 것 같은 느낌이 드는 그런 기업이 매번 더 끌리는건 변하지 않는것 같습니다. ^^; 아무튼 조금은 두서없이 얘기를 드렸는지도 모르지만 개발자로 사회에 입문하시는 분들 또는 사회에 발을 디디신지 얼마 되지 않은 분들이 자신에게 맞는 기업을 잘 선택하시는데 조금이나마 도움이 되시길 바래보겠습니다. 코로나 시대가 다가온것이 안타까운건 저 또한 마찬가지이지만 다른 한편으로는 개발자의 길을 걸어 가시려는 분들께 개발자가 되는것이 지금보다 충분히 더 가치가 있다라는 사실도 덩달아서 보여주는것 같습니다. 모두들 건강 관리 잘 하시고, 그럼 저는 다음에 또 다른 이야기로 찾아뵐게요. 감사합니다.