본문 바로가기
TECH

비동기와 observing ⋲

by Stella-Park 2025. 6. 30.
728x90

비동기 (Asynchronouse)

  • 어떤 작업이 즉시 완료되지 않고, 나중에 완료될 수 있도록 예약해 두는 방식을 말한다. 기다리지 않고 다음 코드를 계속 실행할 수 있어 병렬적 처리나 응답 지연 처리에 적합하다.
  • 실행 흐름을 블로킹(어떤 작업이 완료될 때까지 해당 작업의 실행 흐름을 멈추고 대기하는 것)하지 않는다.
  • Promise, async/await, 콜백(callback) 등이 대표적인 비동기 처리 방식
  • 주로 "작업의 완료 시점"에 관심이 있다.

 

옵저빙 (Observing)

  • 값이나 상태의 변화를 관찰(watch)하고, 그 변화가 발생할 때마다 반응하는 것을 말한다.
  • 비동기와 달리, "이벤트의 스트림(흐름)"을 지속적으로 감시하는 데 초점을 두고 있다.
  • 시간이 흐르면서 발생하는 여러 개의 이벤트(스트림)를 감시한다.
  • 옵저버블(Observable) 객체와 구독(Subscribe) 구조로 이루어진다.
  • reactive programming의 핵심 요소로 상태 변화를 "계속해서 추적"하며 "반응적으로 처리"

 

비동기 vs 옵저빙

항목 비동기 (Asynchronous) 옵저빙 (Observing)
목적 한 번 일어나는 작업을 지연 실행 여러 번 발생하는 이벤트를 감시
초점 작업이 끝났을 때 처리 값이 바뀔 때마다 반응
형태 Promise, async/await, setTimeout 등 Observable, Event Stream, RxJS 등
반응성 없음 (수동적) 있음 (자동 반응)
활용 서버 응답, 파일 읽기 등 UI 이벤트, 데이터 스트림, 상태 관리 등

 

결론

  1. 비동기는 지금 당장 실행하지 않고 나중에 처리하겠다는 의미
  2. 옵저빙은 계속해서 무언가를 지켜보다가, 변하면 반응하겠다는 개념

둘 다 비동기적 흐름에서 사용되지만, 비동기는 단발적, 옵저빙은 지속적이라는 차이가 가장 핵심적인 포인

 

Promise와 async/await가 많이 사용되는데 이 둘의 차이점은 뭘까❓

 

Promise

비동기 작업의 결과를 나중에 사용할 수 있도록 표현한 객체다. 작업의 성공(resolve) 또는 실패(reject)를 표현할 수 있다.

function fetchData() {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve("데이터");
    }, 1000);
  });
}


fetchData().then(data => {
  console.log(data);
}).catch(err => {
  console.error(err);
});

 

 

async/await란?

Promise를 더 동기 코드처럼 보이게 작성할 수 있도록 해주는 문법이다. await는 Promise가 해결될 때까지 기다렸다가 결과를 반환한다.

async function getData() {
  try {
    const data = await fetchData();  // fetchData는 Promise를 반환
    console.log(data);
  } catch (err) {
    console.error(err);
  }
}

getData();

 

Promise와 async/await 비교

항목 Promise async/await
코드 스타일 .then() / .catch() 체이닝 try / catch 구조
가독성 중첩되면 지저분해질 수 있음 (콜백 지옥 비슷하게) 동기 코드처럼 깔끔하게 작성 가능
에러 처리 .catch()를 추가해야 함 try/catch로 자연스럽게 처리
병렬 처리 .then() 체이닝으로 컨트롤 Promise.all()과 같이 함께 사용 필요
디버깅 스택 트레이스가 덜 명확할 수 있음 디버깅이 조금 더 직관적임

 

언제 어떤 걸 써야 할까❓

1️⃣ async/await 추천 상황

  • 비동기 작업을 순차적으로 실행해야 할 때
  • 코드 흐름을 직관적으로 이해하고 싶을 때
  • 복잡한 비동기 로직에 조건문/반복문이 포함되어 있을 때
const res1 = await fetch(...);
const res2 = await fetch(...);

 

2️⃣ Promise 추천 상황

  • 여러 작업을 동시에 실행하고 모두의 완료를 기다릴 때
  • 짧고 간단한 작업을 연결만 하고 싶을 때
  • .then() 체이닝이 더 간결하게 느껴질 때
Promise.all([fetch(...), fetch(...)]).then(([res1, res2]) => {
  ...
});

 

혼용에 주의할 점

async/await를 사용할 때도 내부적으로는 Promise를 사용하기 때문에 혼용이 가능하지만 주의할 필요가 있다 ‼️

 

// 잘못된 예: await 없이 then만 쓰는 혼합 스타일
const data = await fetch(...).then(res => res.json()); // X (불필요하게 섞음)


// 바람직한 예:
const res = await fetch(...);
const data = await res.json(); // 깔끔하게 await 스타일 유지

 

결론

  • async/await은 가독성과 유지보수성에 강점이 있다.
  • Promise는 병렬 처리나 간단한 로직에 적합하다.
  • 실무에서는 async/await을 기본 스타일로 사용하고, 필요할 때 Promise.all, Promise.race 등과 함께 사용하는 패턴이 일반적이다.

 

 

이상 스텔라였습니다. ✍️

 

 

728x90

'TECH' 카테고리의 다른 글

이벤트 트래킹과 헤비포인트 🎭  (7) 2025.07.02
도메인이 다를 때 Cookie 인식 방법 🍪  (13) 2025.07.01
BEM 방법론 📚  (9) 2025.06.27
Reflow와 Repaint 🎨  (2) 2025.06.26
딥링크 🔗  (13) 2025.06.25