Promise를 활용한 데이터 캐싱 기능 개발

개요

데이터 캐싱은 웹 애플리케이션의 성능을 향상시키기 위해 필요한 기능입니다. 데이터를 매번 서버에서 가져오는 대신, 한 번 가져온 데이터는 캐시에 저장하여 다음에 요청이 있을 때 서버에 다시 요청하지 않고 캐시에서 데이터를 가져올 수 있습니다. 이를 통해 불필요한 네트워크 요청을 줄이고 성능을 개선할 수 있습니다.

문제

하지만 데이터 캐싱을 구현하는 과정에서 주의할 점들이 있습니다. 여러 개의 비동기 작업을 동시에 진행하다보면, 캐시에 저장된 데이터가 업데이트되는 시점에는 이전에 진행 중이던 비동기 작업들이 아직 끝나지 않은 상태일 수 있습니다. 이런 상황에서는 업데이트된 데이터가 아닌 이전 데이터를 반환하는 문제가 발생할 수 있습니다.

해결책

이러한 문제를 해결하기 위해 Promise를 활용한 데이터 캐싱 기능을 개발할 수 있습니다. 다음은 코드 예시입니다.

class Cache {
  constructor() {
    this.data = null;
    this.promise = null;
  }

  getData() {
    if (this.data) {
      return Promise.resolve(this.data); // 캐시된 데이터가 있으면 바로 resolve
    } else if (this.promise) {
      // 이미 요청이 진행 중인 경우 해당 Promise 반환
      return this.promise;
    } else {
      // 요청이 처음이라면 새로운 Promise 생성
      this.promise = fetchDataFromServer()
        .then((data) => {
          this.data = data; // 데이터 캐싱
          this.promise = null; // Promise 초기화
          return data;
        })
        .catch((error) => {
          this.promise = null; // Promise 초기화
          throw error;
        });

      return this.promise;
    }
  }
}

// 서버에서 데이터 가져오는 비동기 함수
function fetchDataFromServer() {
  return new Promise((resolve, reject) => {
    // 데이터를 서버에서 가져오는 로직 작성
    // 성공한 경우 resolve(data) 호출
    // 실패한 경우 reject(error) 호출
  });
}

// 데이터 캐싱 예제 코드
const cache = new Cache();

cache.getData()
  .then((data) => {
    // 데이터 사용
  })
  .catch((error) => {
    // 에러 처리
  });

위의 코드 예시에서는 Cache 클래스를 정의하고 getData 메서드를 활용하여 데이터 캐싱을 구현합니다. getData 메서드는 다음과 같은 동작을 수행합니다.

  1. 현재 캐시에 데이터가 있는지 확인합니다. 데이터가 존재하면 바로 Promise.resolve로 데이터를 반환합니다.
  2. 캐시에 데이터가 없을 경우, 이미 요청이 진행 중인지 확인합니다. 진행 중인 요청이 있으면 해당 Promise를 반환합니다.
  3. 요청이 처음이라면 fetchDataFromServer 함수를 호출하여 서버에서 데이터를 가져옵니다. 데이터를 성공적으로 가져오면, 데이터를 캐싱하고 Promise를 해결(resolve)합니다. 만약 데이터를 가져오는 과정에서 에러가 발생하면 Promise를 거부(reject)합니다.

이렇게 구현된 데이터 캐싱 기능은 여러 개의 비동기 작업이 동시에 진행되더라도, 항상 최신 데이터를 반환할 수 있습니다.