본문 바로가기
카테고리 없음

비동기 프로그래밍

by 문자메일 2023. 7. 31.

Async한 통신

실시간성 응답을 필요로 하지 않는 상황에서 사용한다.

ex : Notification, Email 전송, Push 알림 등

 

Main 쓰레드가 task를 처리하는게 아니라, sub thread에게 task를 위임하는 것으로 말할 수 있다.

 

spring에서 비동기 프로그래밍을 위해선 ThreadPool을 정의할 필요가 있다

 

비동기는 Main Thread가 아닌 Sub Thread에서 작업이 진행

Java에서는 ThreadPool을 생성해서 Async 작업을 처리

 

CorePoolSize

MaxPoolSize

WorkQueue

KeepAliveTime

 

ThreadPoolExecutor executorPool = new ThreadPoolExecutor(5, 10, 3, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(50));

 

 

 

 

package com.example.async.service;

import lombok.RequiredArgsConstructor;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;

@Service
@RequiredArgsConstructor
public class AsyncService {

    private final EmailService emailService;

    /*
    [asyncCall_1] :: http-nio-8080-exec-1
    finish
    [messagingTaskExecutor] :: messagingTaskExecutor-1
    [sendMail] :: defaultTaskExecutor-1
     */
    /*
    @Async 메서드가 포함되어 있는 클래스는 비동기 기능을 지원할 수 있도록 스프링 프레임워크가 Wrapping해서 Proxy 객체로
    만들어서 가지고 있기 때문에  asyncCall_1 만 비동기로 하위 스레드에서 실행된 것을 확인 가능하다.
    즉, 반드시 bean 주입을 받아야 한다.
     */
    public void asyncCall_1(){
        System.out.println("[asyncCall_1] :: " + Thread.currentThread().getName());
        emailService.sendMail();
        emailService.sendMailWithCustomThreadPool();
        /*
        - 비동기로 동작할 수 있게 Sub Thread에게 위임
        - emailService.sendMail();
         */
    }

    /*
    [asyncCall_2] :: http-nio-8080-exec-4
    [sendMail] :: http-nio-8080-exec-4
    [messagingTaskExecutor] :: http-nio-8080-exec-4
    finish
     */
    public void asyncCall_2(){
        System.out.println("[asyncCall_2] :: " + Thread.currentThread().getName());
        EmailService emailService = new EmailService();
        emailService.sendMail();
        emailService.sendMailWithCustomThreadPool();
    }

    /*
    [asyncCall_3] :: http-nio-8080-exec-5
    [sendMail] :: http-nio-8080-exec-5
    finish
     */
    public void asyncCall_3(){
        System.out.println("[asyncCall_3] :: " + Thread.currentThread().getName());
        sendMail();
    }

    @Async
    public void sendMail(){
        System.out.println("[sendMail] :: " + Thread.currentThread().getName());
    }
}

댓글