[javascript] 비동기 작업에서의 콜백 함수 대신 프로미스 활용하기

최근에는 비동기 작업을 처리할 때 콜백 함수 대신 프로미스(Promise)를 활용하는 경우가 많아지고 있습니다. 프로미스는 비동기 작업의 결과를 보다 간편하게 처리하고, 코드의 가독성을 향상시킬 수 있는 방법입니다.

콜백 함수의 문제점

콜백 함수를 사용하면 비동기 작업의 결과를 처리하기 위해 중첩된 구문을 작성해야 합니다. 이로 인해 코드의 가독성이 떨어지고, 에러 처리가 복잡해질 수 있습니다. 예를 들어, 다음은 콜백 함수를 사용하여 파일을 읽는 예제입니다.

fs.readFile('example.txt', 'utf-8', function(err, data) {
    if (err) {
        console.error('Error reading file:', err);
    } else {
        console.log('File content:', data);
    }
});

이 예제에서는 파일을 읽는 작업이 완료되면 콜백 함수가 호출되며, 에러가 발생한 경우 에러를 출력하고 파일의 내용을 출력합니다. 하지만 비동기 작업이 여러 개인 경우 콜백 함수가 계속 중첩되어 코드가 복잡해지게 됩니다.

프로미스의 동작 방식

프로미스는 콜백 함수를 사용하지 않고 비동기 작업을 처리할 수 있는 패턴입니다. 프로미스 객체는 작업이 성공적으로 완료되면 resolve 콜백을 호출하고, 작업이 실패한 경우 reject 콜백을 호출합니다. 이를 통해 작업의 성공 또는 실패에 따라 다른 처리를 할 수 있습니다.

프로미스를 사용하여 파일을 읽는 예제를 개선하면 다음과 같습니다.

const fs = require('fs');

function readFile(filename) {
    return new Promise((resolve, reject) => {
        fs.readFile(filename, 'utf-8', (err, data) => {
            if (err) {
                reject(err);
            } else {
                resolve(data);
            }
        });
    });
}

readFile('example.txt')
    .then(data => {
        console.log('File content:', data);
    })
    .catch(err => {
        console.error('Error reading file:', err);
    });

이 예제에서는 readFile 함수를 정의하여 프로미스 객체를 생성하고, 파일을 읽는 작업을 수행합니다. 작업이 완료되면 resolve를 호출하여 파일의 내용을 전달하고, 에러가 발생한 경우 reject를 호출하여 에러를 전달합니다. 이후 then 메서드를 사용하여 작업의 성공 처리, catch 메서드를 사용하여 작업의 실패 처리를 수행합니다.

async/await 문법의 활용

프로미스를 사용하면 비동기 작업의 결과를 처리하는 부분이 then/catch 메서드를 이용하여 연결되어 있으므로 코드가 좀 더 직관적으로 표현됩니다. 또한, async/await 문법을 함께 활용하면 코드를 더욱 간략하고 가독성 있게 작성할 수 있습니다.

다음은 async/await 문법을 활용하여 파일을 읽는 예제입니다.

const fs = require('fs');

async function readFile(filename) {
    try {
        const data = await fs.promises.readFile(filename, 'utf-8');
        console.log('File content:', data);
    } catch (err) {
        console.error('Error reading file:', err);
    }
}

readFile('example.txt');

이 예제에서는 readFile 함수를 async 함수로 정의하고, await 키워드를 사용하여 비동기 작업의 결과를 기다립니다. 작업이 성공적으로 완료되면 data에 결과가 저장되고, 에러가 발생한 경우 catch 블록에서 에러를 처리합니다.

결론

비동기 작업을 처리하는 방법 중 프로미스는 콜백 함수와 비교하여 코드의 가독성과 유지보수성을 향상시킬 수 있는 유용한 기법입니다. 비동기 작업을 처리할 때는 가능하면 프로미스를 활용하고, async/await 문법을 함께 사용하여 좀 더 간결하고 가독성 있는 코드를 작성하는 것을 권장합니다.

References